BigDecimal带精度的运算
来源:百度文库 编辑:神马文学网 时间:2024/04/29 12:53:41
BigDecimal带精度的运算
之前提到过在商业运算中要使用BigDecimal来进行相关的钱的运算(Java中使用BigDecimal进行浮点数高精度计算),可是实际使用中,简单的用BigDecimal还是出现了一些小问题。
Java代码- BigDecimal a = new BigDecimal(998.01);
- BigDecimal b=new BigDecimal("100");
- System.out.println(a.multiply(b));
- BigDecimal aa = new BigDecimal(135.95);
- BigDecimal bb=new BigDecimal("100");
- System.out.println(aa.multiply(bb));
- BigDecimal test = new BigDecimal(4.015);
- BigDecimal test1 = new BigDecimal(100);
- System.out.println(test.multiply(test1));
输出结果为:
- 99800.999999999999090505298227071762084960937500
- 13594.99999999999886313162278383970260620117187500
- 401.49999999999996802557689079549163579940795898437500
出现这种情况的原因就是没有使用BigDecimal的精度。不罗嗦了,直接写上使用BigDecimal的带精度的运算。
比较简单,看代码:
BigDecimal aa = new BigDecimal(135.95);
- BigDecimal bb=new BigDecimal("100");
- BigDecimal result=aa.multiply(bb);
- System.out.println(result.setScale(2,BigDecimal.ROUND_HALF_EVEN));
BigDecimal aa = new BigDecimal(135.95);BigDecimal bb=new BigDecimal("100");BigDecimal result=aa.multiply(bb);System.out.println(result.setScale(2,BigDecimal.ROUND_HALF_EVEN));
此时的输出结果为:13595.00
最主要的是运用了:
Java代码- result.setScale(2,BigDecimal.ROUND_HALF_EVEN)
看一下BigDecimal的setScale的api
BigDecimal的API 写道可以通过两种类型的操作来处理 BigDecimal 的标度:标度/舍入操作和小数点移动操作。标度/舍入操作(setScale 和 round)返回 BigDecimal,其值近似地(或精确地)等于操作数的值,但是其标度或精度是指定的值;即:它们会增加或减少对其值具有最小影响的存储数的精度。小数点移动操作(movePointLeft 和 movePointRight)返回从操作数创建的 BigDecimal,创建的方法是按指定方向将小数点移动一个指定距离。 Java代码- setScale
- public BigDecimal setScale(int newScale,
- int roundingMode)
- 返回一个 BigDecimal,其标度为指定值,其非标度值通过此 BigDecimal 的非标度值乘以或除以十的适当次幂来确定,
- 以维护其总值。如果该操作减少标度,则非标度值必须被除(而不是乘),并且该值可以更改;在这种情况下,将指定的
- 舍入模式应用到除法中。
- 注意,由于 BigDecimal 对象是不可变的,此方法的调用不会 导致初始对象被修改,
- 这与使用名为 setX 变异字段 X 方法的常规约定相反。相反,setScale 返回具有适当标度的对象;
- 返回的对象不一定是新分配的。
- 相对于此遗留方法,应优先使用新的 setScale(int, RoundingMode) 方法。
- 参数:
- newScale - 要返回的 BigDecimal 值的标度。
- roundingMode - 要应用的舍入模式。
- 返回:
- 一个 BigDecimal,其标度为指定值,其非标度值可以通过此 BigDecimal 的非标度值乘以或除以十的适当次幂来确定。
setScalepublic BigDecimal setScale(int newScale,int roundingMode)
返回一个 BigDecimal,其标度为指定值,其非标度值通过此 BigDecimal 的非标度值乘以或除以十的适当次幂来确定,以维护其总值。如果该操作减少标度,则非标度值必须被除(而不是乘),并且该值可以更改;在这种情况下,将指定的舍入模式应用到除法中。注意,由于 BigDecimal 对象是不可变的,此方法的调用不会 导致初始对象被修改,这与使用名为 setX 变异字段 X 方法的常规约定相反。相反,setScale 返回具有适当标度的对象;返回的对象不一定是新分配的。相对于此遗留方法,应优先使用新的 setScale(int, RoundingMode) 方法。参数:newScale - 要返回的 BigDecimal 值的标度。roundingMode - 要应用的舍入模式。返回:一个 BigDecimal,其标度为指定值,其非标度值可以通过此 BigDecimal 的非标度值乘以或除以十的适当次幂来确定。
RoundingMode的API
CEILING
向正无限大方向舍入的舍入模式。
DOWN
向零方向舍入的舍入模式。
FLOOR
向负无限大方向舍入的舍入模式。
HALF_DOWN
向最接近数字方向舍入的舍入模式,如果与两个相邻数字的距离相等,则向下舍入。
HALF_EVEN
向最接近数字方向舍入的舍入模式,如果与两个相邻数字的距离相等,则向相邻的偶数舍入。
HALF_UP
向最接近数字方向舍入的舍入模式,如果与两个相邻数字的距离相等,则向上舍入。
UNNECESSARY
用于断言请求的操作具有精确结果的舍入模式,因此不需要舍入。
UP
远离零方向舍入的舍入模式。
看完这些前面那个:
Java代码
result.setScale(2,BigDecimal.ROUND_HALF_EVEN)
的意思就是,将这个BigDecimal小数点后保留2位,四舍五入的方式为向最接近数字方向舍入的舍入模式,如果与两个相邻数字的距离相等,则向相邻的偶数舍入。
ok,记录完毕,看来以后要用bigDecimal还必须要用它这个scale的功能来保证精度,不然还是跟double一样会出现悲剧!
BigDecimal带精度的运算
博客园 - 喻祥,性情中人 - java浮点运算精度问题的解决
轴承的精度等级
PHP的位运算
JavaScript的四舍五入运算
紫微斗数的运算基础
紫微斗数的运算方法
紫微斗数的运算基础
运算符 的 重载
小麦粉加工精度的检验
不“简单”的“简便运算”
不“简单”的“简便运算”
Delphi 的运算符列表
加减乘除运算符号的来源
人机交互的高精度和低精度原型
SQL中各数据类型的长度、精度
齿轮精度等级、公差的说明
提高步进系统精度的措施
提高步进系统精度的措施
精密轴承安装后的精度
如何提高薄壁零件的加工精度
第四章 [ ]运算符的本质
自增自减运算的用法
[分享]关于Like运算符的使用