我试图使用BigDecimal类来解决一个练习,但是对于一些数值,它不尊重正确的小数点位数。有什么原因吗?先谢谢你。
这是代码的改编版本。
MathContext mc = new MathContext(2, RoundingMode.UP);
BigDecimal min = new BigDecimal("2.00");
BigDecimal adt = new BigDecimal("0.50");
BigDecimal lim = new BigDecimal("3.00");
for (float f = 5f; f <= 30f ; f += 0.5f) {
String s = Float.toString(f);
BigDecimal hours = new BigDecimal(s);
BigDecimal charge = min.add(hours.subtract(lim).round(mc).multiply(adt));
System.out.println(f + " = " + charge);
}
输出
5.0 = 3.000
5.5 = 3.250
6.0 = 3.500
6.5 = 3.750
7.0 = 4.000
7.5 = 4.250
8.0 = 4.500
8.5 = 4.750
9.0 = 5.000
9.5 = 5.250
10.0 = 5.500
10.5 = 5.750
11.0 = 6.000
11.5 = 6.250
12.0 = 6.500
12.5 = 6.750
13.0 = 7.00
13.5 = 7.50
14.0 = 7.50
14.5 = 8.00
15.0 = 8.00
15.5 = 8.50
16.0 = 8.50
16.5 = 9.00
17.0 = 9.00
17.5 = 9.50
18.0 = 9.50
18.5 = 10.00
19.0 = 10.00
19.5 = 10.50
20.0 = 10.50
20.5 = 11.00
21.0 = 11.00
21.5 = 11.50
22.0 = 11.50
22.5 = 12.00
23.0 = 12.00
23.5 = 12.50
24.0 = 12.50
24.5 = 13.00
25.0 = 13.00
25.5 = 13.50
26.0 = 13.50
26.5 = 14.00
27.0 = 14.00
27.5 = 14.50
28.0 = 14.50
28.5 = 15.00
29.0 = 15.00
29.5 = 15.50
30.0 = 15.50
这个问题可能是对 MathContext
. 随着 MathContext(2, RoundingMode.UP)
你不是说"我要2位小数"但你却说我想把数字的精度降低到2位数。".
如果你看一下你的数字,比例(小数点后的位数)是2,其中 hours - lim >= 10
如果你对这两个例子有一个详细的了解 hours=12.5
和 hours=13.0
//hours = 12.5:
var subtract = hours.subtract("3.00"); // 12.5 - 3.00 = 9.50 (subtract.scale = 2)
var round = subtract.round(mc); // 9.5 (round.scale = 1)
var result = round.multiply("0.50") // 9.5 * 0.50 = 4.750 (result.scale = round.scale + subtract.scale = 3)
//hours = 13.0:
var subtract = hours.subtract("3.00"); // 13.0 - 3.00 = 10.00 (subtract.scale = 2)
var round = subtract.round(mc); // 10 (round.scale = 0)
var result = round.multiply("0.50") // 10 * 0.50 = 5.00 (result.scale = round.scale + subtract.scale = 2)
你看四舍五入小数的比例尺一变成>=10,它的值就变成了0。乘法的结果的比例总是两个乘数的比例之和。
要设置一个 BigDecimal
使用 BigDecimal.setScale(int, RoundingMode)
而不是 MathContext
.