BigDecimal 学习笔记

一、核心定位

  • 用途:解决 double/float 精度丢失问题,专门处理高精度小数场景(如金额、税率、礼品卡余额等)。
  • 核心优势:存储精确、计算安全、支持自定义舍入规则和小数位数。

二、创建方式(避坑关键)

创建方式代码示例适用场景注意事项
字符串构造(推荐)new BigDecimal("100.50")金额、复杂小数无精度丢失,最安全
静态方法 valueOf(推荐)BigDecimal.valueOf(100.50)基本类型小数、整数内部转字符串,无精度丢失
double 构造(绝对禁止)new BigDecimal(100.50)无(绝对不用)存在隐藏精度丢失,金额场景禁用

三、核心操作(不可变类,需接收返回值)

1. 加减乘除(金额计算核心)

操作方法代码示例(礼品卡场景)
加法add(BigDecimal val)BigDecimal newBalance = balance.add( rechargeAmount); // 余额 + 充值金额
减法subtract(BigDecimal val)BigDecimal newBalance = balance.subtract(consumeAmount); // 余额 - 消费金额
乘法multiply(BigDecimal val)BigDecimal discountAmount = amount.multiply(new BigDecimal("0.9")); // 9 折
除法divide(除数, 小数位, 舍入模式)BigDecimal split = total.divide(new BigDecimal("3"), 2, RoundingMode.HALF_UP); // 平分,保留 2 位小数

2. 比较大小(禁用 ==

比较场景代码示例结果说明
等于a.compareTo(b) == 0true 表示两值相等
大于a.compareTo(b) > 0true 表示 a > b
大于等于a.compareTo(b) >= 0余额≥消费金额时可用
小于a.compareTo(b) < 0true 表示 a < b

3. 小数位数与格式化

需求代码示例效果
保留 2 位小数(四舍五入)a.setScale(2, RoundingMode.HALF_UP)100.1 → 100.10
千分位 + 2 位小数new DecimalFormat("#,##0.00").format(a)2000.5 → 2,000.50
Hutool 简化格式化NumberUtil.round(a, 2)直接保留 2 位小数,无需手动写模式

四、常用舍入模式(金额场景优先用前 2 个)

模式说明(小白白话版)示例(保留 1 位小数)
RoundingMode.HALF_UP四舍五入(日常常用)100.55 → 100.6
RoundingMode.DOWN直接舍去小数(不进 1)100.59 → 100.5
RoundingMode.UP小数位非 0 则进 1(不舍弃)100.51 → 100.6
RoundingMode.HALF_DOWN五舍六入(少用)100.55 → 100.5

五、小白必避坑

  1. 绝对不用 new BigDecimal(double):避免精度丢失;
  2. 操作后必须接收返回值:BigDecimal 不可变,原对象不会被修改;
  3. 除法必须指定小数位和舍入模式:否则除不尽时抛异常;
  4. 金额统一保留 2 位小数:避免后续计算精度累积;
  5. 禁用 == 比较:必须用 compareTo 方法。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值