当前位置: 首页 > news >正文

Java 中 BigDecimal、Float、Double 的取整与保留小数处理方法详解

在日常的企业级 Java 开发中,浮点数的精度控制与舍入处理常常是财务系统、计量系统、SaaS 计费系统等场景中的核心需求。本文将围绕 BigDecimalFloatDouble 三种常用数值类型,系统性地讲解如何在 Java 中进行“取整处理”以及“保留指定位数的小数”。


一、基础类型概览

类型精度特性适用场景
float约 7 位十进制有效位图形渲染、传感器数据
double约 15 位十进制有效位科学计算、非财务场景中的近似计算
BigDecimal任意精度(定点表示)财务系统、计价、利率、账单

提示floatdouble 属于二进制浮点表示,不能精确表示所有十进制小数,如 0.1 + 0.2 ≠ 0.3BigDecimal 为定点小数,适合需要精确计算的业务场景。


二、取整处理方式(去小数部分)

1. BigDecimal 去整数或保留整数部分

方法一:去掉小数部分,保留整数(向下取整)
BigDecimal value = new BigDecimal("123.4567");
BigDecimal integerPart = value.setScale(0, RoundingMode.DOWN);
System.out.println(integerPart); // 输出 123
方法二:只保留小数部分
BigDecimal decimalPart = value.remainder(BigDecimal.ONE);
System.out.println(decimalPart); // 输出 0.4567

⚠️ 若值为负数,小数部分也为负。可通过 .abs() 获取正的小数部分。


2. Float / Double 去整数(保留整数部分)

double d = 123.4567;
int intPart = (int) d; // 强制转换,直接截断
System.out.println(intPart); // 输出 123

⚠️ 使用 (int) 会舍弃小数部分(向零靠拢),不推荐用于财务计算。


三、保留指定位数的小数

1. BigDecimal 保留两位小数

方式一:使用 setScale
BigDecimal value = new BigDecimal("123.4567");
BigDecimal rounded = value.setScale(2, RoundingMode.HALF_UP);
System.out.println(rounded); // 输出 123.46(四舍五入)
RoundingMode含义
HALF_UP四舍五入(常用)
DOWN直接截断(不进位)
CEILING向上取整(正方向)
FLOOR向下取整(负方向)

2. Float / Double 保留两位小数(⚠️ 仅显示用途)

double d = 123.4567;
String formatted = String.format("%.2f", d);
System.out.println(formatted); // 输出 123.46

📌 本质上没有改变 d 的值,仅用于显示。如果需要数值级的保留精度,请转为 BigDecimal 操作。


3. 将 Double 转为 BigDecimal 后精确控制

double d = 123.4567;
BigDecimal bd = new BigDecimal(Double.toString(d));
BigDecimal rounded = bd.setScale(2, RoundingMode.HALF_UP);
System.out.println(rounded); // 输出 123.46

⚠️ 使用 new BigDecimal(double) 存在二进制浮点误差,应优先使用 BigDecimal.valueOf(double)new BigDecimal(String)


四、实践建议

场景推荐类型原因
财务计算、税率、利息BigDecimal支持任意精度,避免精度丢失
需要高性能、允许误差的小数double性能优先,计算快
保留两位用于展示String.format格式化展示友好

五、通用工具方法示例

public class DecimalUtils {public static BigDecimal keepScale(BigDecimal value, int scale) {return value.setScale(scale, RoundingMode.HALF_UP);}public static BigDecimal getDecimalPart(BigDecimal value) {return value.remainder(BigDecimal.ONE);}public static BigDecimal getIntegerPart(BigDecimal value) {return value.setScale(0, RoundingMode.DOWN);}public static String formatDouble(double val, int scale) {return String.format("%." + scale + "f", val);}
}

六、总结

  • BigDecimal 是进行取整、保留小数等操作的首选,适用于精度要求极高的系统;

  • floatdouble 更适用于对性能有要求但容忍精度误差的场景;

  • 所有涉及货币、计价的系统中,应避免使用 float 和 double 存储金额

  • 所有保留小数位的操作,请优先使用 BigDecimal.setScale 实现,而非 Math.round()String.format()

http://www.dtcms.com/a/313767.html

相关文章:

  • 从 0 到 1 开发图书管理系统:飞算 JavaAI 让技术落地更简单
  • 13.Home-面板组件封装
  • 如何设计和实施高效的向量化数据检索解决方案
  • 阿里云-通义灵码:解锁云原生智能开发新能力,让云开发更“灵”~
  • Clion STM32CubeMX LED闪灯
  • 为什么叫电磁兼容?
  • 【Java】一篇详解HashMap的扩容机制!!
  • SCI论文选词炼句(下)
  • vue3指定设置了dom元素的ref但是为null问题
  • Druid手写核心实现案例 实现一个简单Select 解析,包含Lexer、Parser、AstNode
  • 第三章 浏览器 【5. 事件】
  • Java项目:基于SSM框架实现的电子病历管理系统【ssm+B/S架构+源码+数据库+毕业论文+远程部署】
  • 前端开发(HTML,CSS,VUE,JS)从入门到精通!第五天(jQuery函数库)
  • 深入理解Java的SPI机制,使用auto-service库优化SPI
  • 打造个人数字图书馆:LeaNote+cpolar如何成为你的私有化知识中枢?
  • 【MySQL02】: MySQL类型
  • 深度学习TR3周:Pytorch复现Transformer
  • 软件测试自学之路
  • 架构师面试(三十九):微服务重构单体应用
  • 第三阶段—8天Python从入门到精通【itheima】-143节(pyspark实战——数据计算——flatmap方法)
  • RAG From Scratch 系列教程-4: Query_Construction
  • 向量空间模型
  • 开源的时间跟踪工具TimeTagger
  • PHP进阶语法详解:命名空间、类型转换与文件操作
  • 动态规划技巧:深入解析“组合总和IV”与“不同的二叉搜索树”中的卡特兰数
  • 豆包1.6+PromptPilot实战:构建智能品牌评价情感分类系统的技术探索
  • Jwts用于创建和验证 ​​JSON Web Token(JWT)​​ 的开源库详解
  • 【盘古100Pro+开发板实验例程】FPGA学习 | 基于 UDP 的以太网传输实验例程
  • Oracle 在线重定义
  • git操作命令和golang编译脚本