java - Android:java 舍入错误。不明白为什么?

标签 java android bigdecimal rounding

谁能解释为什么这些“相同”的表达式会返回不同的值?

(new BigDecimal(String.valueOf(131.7d))).multiply(new BigDecimal(String.valueOf(0.95d))).doubleValue() = 125.115

(new BigDecimal(               131.7d )).multiply(new BigDecimal(               0.95d )).doubleValue() = 125.11499999999998

BigDecimal 在它们之间有什么不同?

最佳答案

如果您阅读 API 文档,您会发现 String.valueOf(dobule) 使用 Double.toString(double) 来格式化值。这可能并不明显,但是 Double.toString(double) 在将值格式化为字符串之前对其进行舍入:

How many digits must be printed for the fractional part of m or a? There must be at least one digit to represent the fractional part, and beyond that as many, but only as many, more digits as are needed to uniquely distinguish the argument value from adjacent values of type double. That is, suppose that x is the exact mathematical value represented by the decimal representation produced by this method for a finite nonzero argument d. Then d must be the double value nearest to x; or if two double values are equally close to x, then d must be one of them and the least significant bit of the significand of d must be 0.

结果是 String.valueOf(131.7d) 将返回字符串“131.7”,即使参数的确切值为 131.69999999999998863131622783839702606201171875。这样做的原因是小数不能总是用二进制小数精确表示(与 float 和 double 一起使用)。

因此,new new BigDecimal(String.valueOf(131.7)) 将创建一个精确值为 131.7 的 BigDecimal。 new BigDecimal(131.7) 将创建一个具有精确值 131.69999999999998863131622783839702606201171875 的 BigDecimal。

关于java - Android:java 舍入错误。不明白为什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15685705/

相关文章:

java - 如何使用 jorda 时间将时区转换为 UTC 时区

java - 有效地确定列表中的元素应该被删除

java - String 到 BigNumber 转换,特定解决方案

java - ProGuard 忽略注释默认值

java - 如何从 java 计算 html 表中的行数

java - 有没有办法修复这个无效的模块名称错误?

java - 从未缩放的 long 创建 BigDecimal

java - 格式化字符串java

java - BroadCastReceiver 类上的 NullPointerException;

java - 如何用正确的输出计算java中的 double 值?