基础知识回顾:

BigDecimal.setScale()方法用于格式化小数点
setScale(1)表示保留一位小数,默认用四舍五入方式 
setScale(1,BigDecimal.ROUND_DOWN)直接删除多余的小数位,如2.35会变成2.3 
setScale(1,BigDecimal.ROUND_UP)进位处理,2.35变成2.4 
setScale(1,BigDecimal.ROUND_HALF_UP)四舍五入,2.35变成2.4
setScaler(1,BigDecimal.ROUND_HALF_DOWN)四舍五入,2.35变成2.3,如果是5则向下舍
 
 
下面来说说java中浮点数精度的问题:
float和double类型:
当我们用上述的函数(BigDecimal)进行四舍五入的时候,我们都知道是要看数字的尾数,也就是例如:1.25,如果要保留一位小数的时候,我们要看尾数5,
做四舍五入的时候,无论是1.21,1.22,1.23,1.24还是1.26。。都没有问题,只有到1.25的时候,我们得到的四舍五入的结果是1.24,
分析得出:
当 double x=1.25;的时候,在计算机表示的是1.24999999999,所以当我们四舍五入的时候就会出现等于1.24的情况。
解决方案就是:我们传入BigDecimal函数的时候传入字符串类型就可以啦!例如:BigDecimal.setScale(“1.25”)
 
下面是网上的一个小工具类,很好用!
 

import java.math.BigDecimal;

/**
* 由于Java的简单类型不能够精确的对浮点数进行运算,这个工具类提供精 确的浮点数运算,包括加减乘除和四舍五入。
*/
public class Arith {
// 默认除法运算精度
private static final int DEF_DIV_SCALE = 10;

// 这个类不能实例化
private Arith() {
}

/**
* 提供精确的加法运算。
*
* @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();
}

/**
* 提供(相对)精确的除法运算,当发生除不尽的情况时,精确到 小数点以后10位,以后的数字四舍五入。
*
* @param v1
* 被除数
* @param v2
* 除数
* @return 两个参数的商
*/
public static double div(double v1, double v2) {
return div(v1, v2, DEF_DIV_SCALE);
}

/**
* 提供(相对)精确的除法运算。当发生除不尽的情况时,由scale参数指 定精度,以后的数字四舍五入。
*
* @param v1
* 被除数
* @param v2
* 除数
* @param scale
* 表示表示需要精确到小数点以后几位。
* @return 两个参数的商
*/
public static double div(double v1, double v2, int scale) {
if (scale < 0) {
throw new IllegalArgumentException(
"The scale must be a positive integer or zero");
}
BigDecimal b1 = new BigDecimal(Double.toString(v1));
BigDecimal b2 = new BigDecimal(Double.toString(v2));
return b1.divide(b2, scale, BigDecimal.ROUND_HALF_UP).doubleValue();
}

/**
* 提供精确的小数位四舍五入处理。
*
* @param v
* 需要四舍五入的数字
* @param scale
* 小数点后保留几位
* @return 四舍五入后的结果
*/
public static double round(double v, int scale) {
if (scale < 0) {
throw new IllegalArgumentException(
"The scale must be a positive integer or zero");
}
BigDecimal b = new BigDecimal(Double.toString(v));
BigDecimal one = new BigDecimal("1");
return b.divide(one, scale, BigDecimal.ROUND_HALF_UP).doubleValue();
}
}

 

java浮点数精度问题解决方法的更多相关文章

  1. Java 浮点数精度丢失

    Java 浮点数精度丢失 问题引入 昨天帮室友写一个模拟发红包抢红包的程序时,对金额统一使用的 double 来建模,结果发现在实际运行时程序的结果在数值上总是有细微的误差,程序运行的截图: 输入依次 ...

  2. Java 浮点数精度控制

    1.String.format​(String format,Object… args) Java中用String.format()来控制输出精度, format参数用来设置精度格式, args参数代 ...

  3. js,java,浮点数运算错误及应对方法

    js,java浮点数运算错误及应对方法 一,浮点数为什么会有运算错误 IEEE 754 标准规定了计算机程序设计环境中的二进制和十进制的浮点数自述的交换.算术格式以及方法. 现有存储介质都是2进制.2 ...

  4. Java浮点数float,bigdecimal和double精确计算的精度误差问题总结

    (转)Java浮点数float,bigdecimal和double精确计算的精度误差问题总结 1.float整数计算误差 案例:会员积分字段采用float类型,导致计算会员积分时,7位整数的数据计算结 ...

  5. java绘图原理------在窗口界面(或面板上)画出一张或多张图片问题解决方法

    /** *@author blovedr * 功能: java绘图原理------在窗口界面(或面板上)画出一张或多张图片问题解决方法 * 日期: 2018年4月28日     16:20 * 注释: ...

  6. 计算价格, java中浮点数精度丢失的解决方案

    计算价格, java中浮点数精度丢失的解决方案

  7. Java/JSP程序连接不上Mysql驱动问题解决方法

    错误提示: java.lang.ClassNotFoundException: com.mysql.jdbc.Driverat java.net.URLClassLoader$1.run(URLCla ...

  8. Java中FTPClient上传中文目录、中文文件名乱码问题解决方法【好用】

    转: Java中FTPClient上传中文目录.中文文件名乱码问题解决方法 问题描述: 使用org.apache.commons.net.ftp.FTPClient创建中文目录.上传中文文件名时,目录 ...

  9. java浮点数剖析

    定点数表达法的缺点在于其形式过于僵硬,固定的小数点位置决定了固定位数的整数部分和小数部分,不利于同时表达特别大的数或者特别小的数.计算机系统采纳了所谓的浮点数表达方式.这种表达方式利用科学计数法来表达 ...

随机推荐

  1. ccpc湘潭邀请赛 Partial Sum

    选定最多m的区间,使区间和的绝对值最大.但是左右端点不能重复选取 首先涉及到区间和的问题,就应该想到用前缀和去优化 这里对前缀和排序 然后贪心的去选取最大.次大 (比赛的时候脑子堵的很,没想出来 可惜 ...

  2. ModbusTCP报文详解【一】

    [1]功能码01H [2]功能码02H [3]功能码03H [4]功能码04H

  3. 【ES6 】const命令

    本质 const实际上保证的,并不是变量的值不得改动,而是变量指向的那个内存地址所保存的数据不得改动. 对于简单类型的数据(数值.字符串.布尔值),值就保存在变量指向的那个内存地址,因此等同于常量. ...

  4. Advanced Installer 不弹出预安装的软件的窗口

    需求:当他电脑上没有sql server client 的时候,或没有localdb的时候,那么安装包会弹出窗口,让他选择 一个组件 一个组件的安装 太麻烦. 有没有办法,打开安装包就安装 安装的过程 ...

  5. 深入探讨java的类加载器

    类加载器是 Java 语言的一个创新,也是 Java 语言流行的重要原因之一.它使得 Java 类可以被动态加载到 Java 虚拟机中并执行.类加载器从 JDK 1.0 就出现了,最初是为了满足 Ja ...

  6. vue中ref-父主动取值值;

    多用月input标签 定义的时候 直接写ref=“id” <el-input placeholder="请输入内容" style="width: 150px&quo ...

  7. JQ报错:Uncaught SyntaxError: Illegal continue statement: no surrounding iteration statement报错

    今天在写轮播图中,在停止定时器之后想要重新开启定时器,但是不知道为什么脑子抽了竟然想通过continue跳出定时器的本次运行继续下一次运行(当然是不可取的,但是还是试了试2333),然后就报错了.Un ...

  8. 解决'androidx.arch.core:core-runtime' has different version for the compile (2.0.0) and runtime (2.0.1)

    先说原因,我们引用的包版本不同产生了冲突,所以编译不通过.解决的办法是在引用的时候排除一个版本,只留一个版本. 解决过程: 先找出哪些库引用了相同的库,仅仅是版本不同. gradle app:depe ...

  9. SSH安装配置

    一.环境准备 二.SSH配置 1.root用户进入home目录,确实有无隐藏文件夹 .ssh cd ~ ls -lrta 2.有,则跳过本步骤:没有,执行如下命令 ##根据提示输入当前用户密码 ssh ...

  10. Delphi 配置BDE数据源

    樊伟胜