【问题标题】:String to 32 bit Integer in Java, with default value than exceptionJava中的字符串到32位整数,默认值比异常
【发布时间】:2018-12-20 00:28:51
【问题描述】:

我有一串有符号整数值,范围从“+2147483650”到“-9638527412”。我需要将它们解析为 32 位整数,这样,当字符串值高于整数容量 (2^31) 时,它应该返回最接近的可能整数值。使用“Integer.parseInt”会给出超出范围的异常。

示例:

input: "+2147483650"
output: "+2147483647"
input: ""-963852741258"
output: "-2147483648"

我尝试使用现有功能,但我被困在这里。


try{
    //num =Integer.valueOf(stringNumber);
    num =Integer.parseInt(stringNumber);
}catch(Exception e){
    num = -2147483648; // if stringNumber is negative
    num = +2147483647 // if stringNumber is positive
}
  

  

【问题讨论】:

  • 使用BigInteger.valueOf,然后酌情将其与Integer.MAX_VALUEMIN_VALUE 进行比较?
  • @LouisWasserman @LouisWasserman 不会比 BigInteger 更高效,因为它可能使用原生 64 位字而不是专为任意(无限)精度设计的类?
  • @Andreas 超出了 OP 指定的有效输入范围

标签: java string parsing int


【解决方案1】:

由于您的值范围仅限于"+2147483650""-9638527412",您可以解析为long 并检查是否溢出。

public static int parse(String stringNumber) {
    long value = Long.parseLong(stringNumber);
    return (value < Integer.MIN_VALUE ? Integer.MIN_VALUE :
            value > Integer.MAX_VALUE ? Integer.MAX_VALUE : (int) value);
}

测试

System.out.println(parse("+2147483650"));
System.out.println(parse("42"));
System.out.println(parse("-9638527412"));

输出

2147483647
42
-2147483648

【讨论】:

  • 啊,现在你同意我的看法了! ;-)
  • @Alnitak 当然,这就是我删除错误评论的原因。 :-)
  • @Andreas 谢谢,我决定选择 Biginteger,因为我的价值范围也超出了“长期”。这是我实现的最终代码。 BigInteger 值 = 新 BigInteger(stringNumber); return ((BigInteger.valueOf(Integer.MIN_VALUE).compareTo(value) >0)?Integer.MIN_VALUE : (BigInteger.valueOf(Integer.MAX_VALUE).compareTo(value)
【解决方案2】:

如果您没有理由不能使用更大的数据类型,例如Long,那么您可以将其解析为Long。如果解析失败,它会抛出一个NumberFormatException

try {
    long tmp = Long.parseLong(stringNumber);

    int result;
    if (tmp < Integer.MIN_VALUE) {
        result = Integer.MIN_VALUE;
    } else if (tmp > Integer.MAX_VALUE) {
        result = Integer.MAX_VALUE;
    } else {
        // safe cast to int (java 8)
        result = Math.toIntExact(tmp);
    }
    // TODO do something with the result
} catch (NumberFormatException e) {
    // could not parse
}

【讨论】:

    【解决方案3】:

    给定指定的潜在输入范围,该函数会将给定字符串钳制在[Integer.MIN_VALUE, Integer.MAX_VALUE]范围内:

    static int clampedStringValue(String s) {
            long n = Long.parseLong(s);
            if (n > Integer.MAX_VALUE) {
                    return Integer.MAX_VALUE;
            } else if (n < Integer.MIN_VALUE) {
                    return Integer.MIN_VALUE;
            } else {
                    return (int)n;
            }
    }
    

    【讨论】:

    • 为什么要将值装箱到Long 只是为了立即自动拆箱?
    • @Andreas 主要来自复制使用 Integer.valueOf() 而不是 Integer.parseInt 的 OP 代码行 - Long.parseLong 确实会更好。和一些睡眠一样:p
    猜你喜欢
    • 2016-07-28
    • 1970-01-01
    • 2015-03-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多