【问题标题】:BigDecimal 1.0E+8 / 100000000 with ROUND_HALF_UP is 0BigDecimal 1.0E+8 / 100000000 ROUND_HALF_UP 为 0
【发布时间】:2015-02-25 17:45:01
【问题描述】:

有人能解释一下为什么第一行的结果是 0 吗?

System.out.println((new BigDecimal("1.0E+8")).divide(new BigDecimal(100000000), BigDecimal.ROUND_HALF_UP));
System.out.println((new BigDecimal("1.0E+8")).subtract(BigDecimal.ONE).divide(new BigDecimal(100000000), BigDecimal.ROUND_HALF_UP));

0E+7
1

【问题讨论】:

  • 为什么是“0E+7”而不是“0”?
  • @user2864740 那 输出,但我认为 OP 期望 1

标签: java rounding bigdecimal divide


【解决方案1】:

这一切都与所涉及的BigDecimals 的尺度有关。

当您在constructor that takes a String 中指定指数格式时,刻度可能为负数。这表明有效数字不会一直延伸到单位。

BigDecimal oneEPlus8 = new BigDecimal("1.0E+8");
System.out.println(oneEPlus8.scale());

这会输出-7

使用constructor that takes an int 产生0 的比例。

BigDecimal oneHundredMillion = new BigDecimal(100000000);
System.out.println(oneHundredMillion.scale());

这会输出0

当您divide BigDecimals 时,商取调用divide 的对象的比例。所以,商的比例也是-7。结果计算为1,但在-7 的范围内,四舍五入只给出两个选项:010000000,所以ROUND_HALF_UP 舍入为0,输出为0E+7

当您subtract BigDecimals 时,差值取被减去的数字比例的最大值。所以,差异的规模是0。结果计算为10 的比例在此处不强制舍入。输出为1

要得到结果1 而不必减去1,您可以减去0,或者您可以在oneEPlus8 上调用setScale(0)

oneEPlus8 = oneEPlus8.setScale(0);
System.out.println(oneEPlus8.divide(oneHundredMillion, BigDecimal.ROUND_HALF_UP));

这个输出:

1

顺便说一句,您可以使用divide(BigDecimal, RoundingMode) 来划分指定RoundingMode 枚举而不是旧的int 常量。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-01-10
    • 2011-06-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多