如何获得BigDecimal变量的最大可能值?(最好是以编程方式,但硬编码也可以)
编辑
好了,刚才意识到没有这样的东西,因为BigDecimal是任意精度.所以我最终得到了这个,这对我的目的来说足够好了:
BigDecimal my = BigDecimal.valueOf(Double.MAX_VALUE)
在完成上一次开发的代码训练之后,我意识到我需要将所有基于钱的列移动到不使用浮点数学.在Java方面,这意味着使用BigDecimal,但在使用Hibernate/JPA和MySQL 5时,什么是适当的MySQL数据类型来制作该列?
我想设置两个BigDecimal数字a和b.如在这个例子中:
BigDecimal a = new BigDecimal("2.6E-1095");
BigDecimal b = new BigDecimal("2.7E-1105");
int i = 112, j=1;
BigDecimal aa = a.setScale(i+j);
BigDecimal bb = b.setScale(i+j);
Run Code Online (Sandbox Code Playgroud)
当我运行时,我有这个例外:
java.lang.ArithmeticException: Rounding necessary
at java.math.BigDecimal.divideAndRound(BigDecimal.java:1439)
at java.math.BigDecimal.setScale(BigDecimal.java:2394)
at java.math.BigDecimal.setScale(BigDecimal.java:2437)
Run Code Online (Sandbox Code Playgroud)
为什么需要舍入?如果我不想解决,请问什么是解决方案?
谢谢
一些有趣的观察wrt等于0和0.0上的运算符
new Double(0.0).equals(0)返回false,同时new Double(0.0).equals(0.0)返回true.
BigDecimal.ZERO.equals(BigDecimal.valueOf(0.0))返回false,同时BigDecimal.ZERO.equals(BigDecimal.valueOf(0))返回true.
看起来在两种情况下都进行了字符串比较.任何人都可以对此有所了解.
谢谢.
在我的代码中进行了一系列计算之后,我有了一个BigDecimal有价值的东西0.01954
然后我需要将其乘以BigDecimal,100并希望计算值为1.95
我不希望执行任何向上或向下舍入,我只是希望截断超过两位小数的任何值
我尝试将比例设置为2,但后来我得到一个ArithmeticException说法四舍五入是必要的.如何在不指定舍入的情况下设置比例?
我认为java.math.BigDecimal应该是The Answer™需要用十进制数执行无限精度算术.
请考虑以下代码段:
import java.math.BigDecimal;
//...
final BigDecimal one = BigDecimal.ONE;
final BigDecimal three = BigDecimal.valueOf(3);
final BigDecimal third = one.divide(three);
assert third.multiply(three).equals(one); // this should pass, right?
Run Code Online (Sandbox Code Playgroud)
我希望assert通过,但事实上执行甚至没有到达那里:one.divide(three)原因ArithmeticException被抛出!
Exception in thread "main" java.lang.ArithmeticException:
Non-terminating decimal expansion; no exact representable decimal result.
at java.math.BigDecimal.divide
Run Code Online (Sandbox Code Playgroud)
事实证明,API中明确记录了此行为:
在这种情况下
divide,准确的商可能有一个无限长的十进制扩展; 例如,1除以3.如果商具有非终止十进制扩展并且指定操作以返回精确结果,ArithmeticException则抛出a.否则,返回除法的确切结果,与其他操作一样.
进一步浏览API,人们发现实际上有各种重载divide执行不精确的划分,即:
final BigDecimal third = one.divide(three, 33, RoundingMode.DOWN);
System.out.println(three.multiply(third));
// prints "0.999999999999999999999999999999999"
Run Code Online (Sandbox Code Playgroud)
当然,现在显而易见的问题是"有什么意义?".BigDecimal当我们需要 …
我必须将德语区域设置格式化的String转换为BigDecimal.但是,我正在努力寻找最佳解决方案.
以下代码显示了我的问题:
String numberString = "2.105,88";
NumberFormat nf = NumberFormat.getInstance(Locale.GERMAN);
try {
Number parsed = nf.parse(numberString);
BigDecimal bd1 = new BigDecimal(parsed.toString());
System.out.println(bd1.toString());
BigDecimal bd2 = new BigDecimal(parsed.doubleValue());
System.out.println(bd2);
BigDecimal bd3 = new BigDecimal(numberString);
System.out.println(bd3);
} catch (ParseException e) {
e.printStackTrace();
}
Run Code Online (Sandbox Code Playgroud)
这个的出局是
2105.88
2105.8800000000001091393642127513885498046875
java.math.BigDecimal中的java"主要"java.lang.NumberFormatException中的异常java.math.BigDecimal.(未知来源)test.BigDecimalTest.main(BigDecimalTest.java:22)
第一输出是正确的,但它并没有真正意义的一个转换String到Number(Double要准确),然后回String再次,然后进入特定类型的Number,BigDecimal.
第二个输出不正确,但可以通过设置BigDecimal的比例来解决.但是,数字量并不总是已知.
第三个输出显然不是我想要的.
我的问题是,最好的方法是什么?有没有更好的方法来做到这一点?
这不是关于如何比较两个BigDecimal对象的问题 - 我知道你可以使用compareTo而不是equals这样做,因为equals记录为:
与compareTo不同,此方法仅考虑两个BigDecimal对象的值和比例相等(因此通过此方法比较时2.0不等于2.00).
问题是:为什么equals以这种看似违反直觉的方式指定了?也就是说,为什么能够区分2.0和2.00 很重要?
似乎必须有这样的理由,因为Comparable指定compareTo方法的文档指出:
强烈建议(尽管不要求)自然排序与equals一致
我想必须有一个很好的理由忽略这个建议.
我想要一个函数来转换Bigdecimal 10.12 for 10.12345和10.13 for 10.12556.但是没有功能同时满足两种转换.请帮助实现这一目标.
以下是我的尝试.
值10.12345:
BigDecimal a = new BigDecimal("10.12345");
a.setScale(2, BigDecimal.ROUND_UP)
a.setScale(2, BigDecimal.ROUND_CEILING)
a.setScale(2, BigDecimal.ROUND_DOWN)
a.setScale(2, BigDecimal.ROUND_FLOOR)
a.setScale(2, BigDecimal.ROUND_HALF_DOWN)
a.setScale(2, BigDecimal.ROUND_HALF_EVEN)
a.setScale(2, BigDecimal.ROUND_HALF_UP)
Run Code Online (Sandbox Code Playgroud)
输出:
10.12345::10.13
10.12345::10.13
10.12345::10.12
10.12345::10.12
10.12345::10.12
10.12345::10.12
10.12345::10.12
Run Code Online (Sandbox Code Playgroud)
值10.12556:
BigDecimal b = new BigDecimal("10.12556");
b.setScale(2, BigDecimal.ROUND_UP)
b.setScale(2, BigDecimal.ROUND_CEILING)
b.setScale(2, BigDecimal.ROUND_DOWN)
b.setScale(2, BigDecimal.ROUND_FLOOR)
b.setScale(2, BigDecimal.ROUND_HALF_DOWN)
b.setScale(2, BigDecimal.ROUND_HALF_EVEN)
b.setScale(2, BigDecimal.ROUND_HALF_UP)
Run Code Online (Sandbox Code Playgroud)
输出:
10.12556::10.13
10.12556::10.13
10.12556::10.12
10.12556::10.12
10.12556::10.12
10.12556::10.12
10.12556::10.12
Run Code Online (Sandbox Code Playgroud) 执行以下代码:
new BigDecimal(0.06 * 3).toString()
Run Code Online (Sandbox Code Playgroud)
返回0.179999999999999993338661852249060757458209991455078125而不是0.18.
执行
new BigDecimal(0.06).multiply(new BigDecimal(3)).toString()
Run Code Online (Sandbox Code Playgroud)
返回相同的结果.
这怎么可能?