You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java中Object转Double如何避免舍入?数值精度异常求助

问题根源与解决方案

为什么会出现这个错误?

double类型的有效精度仅为15-17位,你要存储的数值12334555578912349.13整数部分就有16位,加上小数部分后,double无法精确表示该数值,会自动将其转换为最接近的可存储近似值。此时你再把这个失真的double值转成BigDecimal,自然得不到预期结果。

解决方法

要避免精度丢失,必须跳过double中转,直接基于精确的字符串形式创建BigDecimal,因为字符串可以完整保留所有数字信息。

修正后的代码示例

如果你的num原本就是字符串形式(建议用这种方式存储高精度数值):

Object num = "12334555578912349.13";
BigDecimal result = new BigDecimal(num.toString())
    .setScale(2, RoundingMode.HALF_EVEN); // 推荐使用枚举类替代旧常量
System.out.println(result);

如果num的类型不确定,可先做类型判断再处理:

Object num = "12334555578912349.13";
BigDecimal result;
if (num instanceof String) {
    result = new BigDecimal((String) num)
        .setScale(2, RoundingMode.HALF_EVEN);
} else if (num instanceof Number) {
    // 仅当数值在double精度范围内时使用此分支,否则仍会失真
    result = BigDecimal.valueOf(((Number) num).doubleValue())
        .setScale(2, RoundingMode.HALF_EVEN);
} else {
    throw new IllegalArgumentException("不支持的数值类型");
}
System.out.println(result);

注:BigDecimal.ROUND_HALF_EVEN是旧版常量,Java 1.5及以后推荐使用RoundingMode.HALF_EVEN枚举,语义更清晰。

内容的提问来源于stack exchange,提问作者Aleyna

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.04 09:35:21