简单BigDecimal运算精度
项目中遇到了数值运算,如网上所写的,一般有这几个方法:
/**
* 提供精确的加法运算。
* @param v1 被加数
* @param v2 加数
* @return 两个参数的和
*/
public static double add(double v1, double v2) {
BigDecimal b1 = new BigDecimal(Double.toString(v1));
BigDecimal b2 = new BigDecimal(Double.toString(v2));
return (b1.add(b2)).doubleValue();
}
/**
* 提供精确的减法运算。
* @param v1 被减数
* @param v2 减数
* @return 两个参数的差
*/
public static double sub(double v1, double v2) {
BigDecimal b1 = new BigDecimal(Double.toString(v1));
BigDecimal b2 = new BigDecimal(Double.toString(v2)); return (b1.subtract(b2)).doubleValue();
}
/**
* 提供精确的乘法运算。
* @param v1 被乘数
* @param v2 乘数
* @return 两个参数的积
*/
public static double mul(double v1, double v2) {
BigDecimal b1 = new BigDecimal(Double.toString(v1));
BigDecimal b2 = new BigDecimal(Double.toString(v2));
return (b1.multiply(b2)).doubleValue();
}
/**
* 提供(相对)精确的除法运算。当发生除不尽的情况时,由scale参数指
* 定精度,以后的数字四舍五入。
* @param v1 被除数
* @param v2 除数
* @param scale 表示需要精确到小数点以后几位。
* @return 两个参数的商
*/
public static double div(double v1, double v2, int scale) {
if (scale < 0) {
System.err.println("除法精度必须大于0!");
return 0;
}
BigDecimal b1 = new BigDecimal(Double.toString(v1));
BigDecimal b2 = new BigDecimal(Double.toString(v2));
return (b1.divide(b2, scale, BigDecimal.ROUND_HALF_UP)).doubleValue();
}
但是这里,我还有两个地方需要做一些变化:
1、乘法运算需要做精度的四舍五入
2、double会自动进行科学计数法
对于第一点新增mul方法
public static double mul(double v1, double v2,int scale) {
BigDecimal b1 = new BigDecimal(Double.toString(v1));
BigDecimal b2 = new BigDecimal(Double.toString(v2));
return (b1.multiply(b2).setScale(scale, RoundingMode.HALF_UP)).doubleValue();
}
这样就可以对所做的运算进行需要的精度的四舍五入
第二点新增double2Str方法
private static String double2Str(double number)
{
return DecimalFormat.getInstance().format(number).replace(",","");
}
不需要进行格式化,因为项目中把科学计数法的数字传给客户端.Net接收,无法正确转换成数值(除非客户端特殊处理这个科学计数法数值)
当时,对第一点做了一个错误的精度处理:MathContext
public static double mul(double v1, double v2,int scale) {
BigDecimal b1 = new BigDecimal(Double.toString(v1));
BigDecimal b2 = new BigDecimal(Double.toString(v2));
return b1.multiply(b2, new MathContext(scale,RoundingMode.HALF_UP)).doubleValue();
}
这个MathContext是从左边第一个数开始算起,而不是从小数点后开始算
补充一下舍入RoundingMode
在RoundingMode中HALF_DOWN 没有按照我预期的对数值进行向下取数值有点疑惑
double d3 = 102207767.555;
d3=new BigDecimal(d3).setScale(2,RoundingMode.HALF_DOWN).doubleValue();
打印后d3显示102207767.56 不应该是102207767.55?
ROUND_CEILING
Rounding mode to round towards positive infinity.
向正无穷方向舍入
ROUND_DOWN
Rounding mode to round towards zero.
向零方向舍入
ROUND_FLOOR
Rounding mode to round towards negative infinity.
向负无穷方向舍入
ROUND_HALF_DOWN
Rounding mode to round towards "nearest neighbor" unless both neighbors are equidistant, in which case round down.
向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,向下舍入, 例如1.55 保留一位小数结果为1.5
ROUND_HALF_EVEN
Rounding mode to round towards the "nearest neighbor" unless both neighbors are equidistant, in which case, round towards the even neighbor.
向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,如果保留位数是奇数,使用ROUND_HALF_UP ,如果是偶数,使用ROUND_HALF_DOWN
ROUND_HALF_UP
Rounding mode to round towards "nearest neighbor" unless both neighbors are equidistant, in which case round up.
向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,向上舍入, 1.55保留一位小数结果为1.6
ROUND_UNNECESSARY
Rounding mode to assert that the requested operation has an exact result, hence no rounding is necessary.
计算结果是精确的,不需要舍入模式
ROUND_UP
Rounding mode to round away from zero.
向远离0的方向舍入
简单BigDecimal运算精度的更多相关文章
- BigDecimal带精度的运算的两篇文章
转自:http://guoliangqi.iteye.com/blog/670908 之前提到过在商业运算中要使用BigDecimal来进行相关的钱的运算(java中关于浮点运算需要注意的 ),可是实 ...
- 关于java中Double类型的运算精度问题
标题 在Java中实现浮点数的精确计算 AYellow(原作) 修改 关键字 Java 浮点数 精确计算 问题的提出:如果我们编译运行下面这个程序会看到什么?publi ...
- 160918、BigDecimal运算
java.math.BigDecimal.BigDecimal一共有4个够造方法,让我先来看看其中的两种用法: 第一种:BigDecimal(double val)Translates a doubl ...
- 关于java中Double类型的运算精度问题(转)
Java Java double:浮点数:精确计算 public class Test{ public static void main(String args[]){ Syst ...
- #define与运算精度问题探究
#include <stdio.h> #define SQR(X) X*X int main(int argc, char* argv[]) { ; ; ; printf("SQ ...
- 搞懂js中小数运算精度问题原因及解决办法
js小数运算会出现精度问题 js number类型 JS 数字类型只有number类型,number类型相当于其他强类型语言中的double类型(双精度浮点型),不区分浮点型和整数型. number类 ...
- JavaScript 浮点数及运算精度调整总结
JavaScript 浮点数及运算精度调整总结 JavaScript 只有一种数字类型 Number,而且在Javascript中所有的数字都是以IEEE-754标准格式表示的.浮点数的精度问题不是J ...
- PHP浮点数运算精度造成的,订单金额支付经常少1分的问题
最近碰见一个奇怪的问题,商城通过微信支付的订单经常少一分钱,经过排查是PHP浮点运算精度问题造成的 由PHP浮点数运算精度造成的,鸟哥的Bolg有详细的说明.http://www.laruence.c ...
- Java 避免精度丢失之BigDecimal 运算
* 由于Java的简单类型不能够精确的对浮点数进行运算,这个工具类提供精确的浮点数运算,包括加减乘除和四舍五入 import java.math.BigDecimal; /** 计算工具类 */ pu ...
随机推荐
- JSP开发模式2(计算器)
CalculatorBean———————————————————————————————————————————— public class CalculatorBean { private ...
- SimpleDateFormat的应用
import java.text.SimpleDateFormat;import java.util.Date;public class Main { public static void ma ...
- jquery验证
首先要引用js库 <script src="js/jquery-1.7.2.min.js"></script> jquery验证方式 function ch ...
- svn ignore
工程名为simple,采用maven进行依赖管理,在check in时我不想工程下maven产生的target目录被提交到SVN(包括目录下所有文件和目录本身). 解决方法: 要被忽略的目录必须是未版 ...
- asp.net下AjaxMethod的使用方法
使用AjaxMethod可以在客户端异步调用服务端方法,简单地说就是在JS里调用后台.cs文件里的方法, 做一些JS无法做到的操作,如查询数据库 使用AjaxMethod要满足一下几点: 1.如果还没 ...
- 用muduo实现memcached协议的例子
最近花了两天时间用 muduo 部分实现了 memcached 服务器协议,代码位于 examples/memcached/server,能通过 memcached 的大部分测试用例(incr/dec ...
- Caffe入门与应用 by GX
深度学习几大工具:Theano(基于python),Torch,Caffe(用c++写的),Tensor flow,CNTK:caffe是比较流行的深度学习的框架 caffe特点:特别适合于新手,由于 ...
- Oracle 身份证校验
SELECT SUBSTR('&AI', 0, 17) || TRANSLATE(DECODE(MOD(SUM(SUBSTR(WI, REGEXP_INSTR(WI, ' ', 1, I) + ...
- sql2000 (附加数据库)错误9003:LSN(434:94:1)无效和数据库置疑处理
由于工作需要更换公司的服务器,于是经过一堆的动作,转移网页,转移数据……正当一切都有序进行,却卡在数据库这里,一般为了方便我对数据库的备份都是复制数据库文件的,再通过附加方法实现的,今天由于发现数据库 ...
- Windows 结构化异常
结构化异常不能用于需要调用对象析构函数的函数中 __try{ } __except(){ } __try{ } __finally{ }