使用 BigDecimal 计算及其格式化

2023-01-28 补充:toString 和 MessageFormat 等方法。

介绍

本文主要记录下 BigDecimalDecimalFormat 类的用法,方便下次使用。

  • BigDecimal 可以更精确的进行小数点运算。
  • DecimalFormat 可以更好的进行与科学计算法之间的换算和保留有效数字。

BigDecimal

加减乘除等

import java.math.BigDecimal;

new BigDecimal("3.1").add(new BigDecimal("1.2"));//加
new BigDecimal("3.1").subtract(new BigDecimal("1.2"));//减
new BigDecimal("3.1").multiply(new BigDecimal("1.2"));//乘
new BigDecimal("3.1").divide(new BigDecimal("1.2"), 2);//除
new BigDecimal("3.1").max(new BigDecial("1.2"));//最大值
new BigDecimal("3.1").min(new BigDecial("1.2"));//最小值
new BigDecimal("3.1").abs();//绝对值
new BigDecimal("3.1").compareTo(new BigDecimal("1.2"));//比较

注意:

  1. BigDecimal 必须为有理数,所以除法最好设置小数位数,否则可能会报错。

四舍五入

BigDecimal.ROUND_UP:不降低计算值的大小(和正负无关)

//不降低计算值的大小(不考虑负号)
new BigDecimal("1.345").setScale(2, BigDecimal.ROUND_UP); //1.35
new BigDecimal("1.346").setScale(2, BigDecimal.ROUND_UP); //1.35
new BigDecimal("-1.345").setScale(2, BigDecimal.ROUND_UP); //-1.35
new BigDecimal("-1.346").setScale(2, BigDecimal.ROUND_UP); //-1.35

BigDecimal.ROUND_DOWN:不增加计算值的大小(和正负无关)

//不增加计算值的大小(不考虑负号)
new BigDecimal("1.345").setScale(2, BigDecimal.ROUND_DOWN); //1.34
new BigDecimal("1.346").setScale(2, BigDecimal.ROUND_DOWN); //1.34
new BigDecimal("-1.345").setScale(2, BigDecimal.ROUND_DOWN); //-1.34
new BigDecimal("-1.346").setScale(2, BigDecimal.ROUND_DOWN); //-1.34

BigDecimal.ROUND_CEILING:不降低值的大小

//不降低值的大小
new BigDecimal("1.345").setScale(2, BigDecimal.ROUND_CEILING); //1.35
new BigDecimal("1.346").setScale(2, BigDecimal.ROUND_CEILING); //1.35
new BigDecimal("-1.345").setScale(2, BigDecimal.ROUND_CEILING); //-1.34
new BigDecimal("-1.346").setScale(2, BigDecimal.ROUND_CEILING); //-1.34

BigDecimal.ROUND_FLOOR:不增加计算值的大小

//不增加计算值的大小
new BigDecimal("1.345").setScale(2, BigDecimal.ROUND_FLOOR); //1.34
new BigDecimal("1.346").setScale(2, BigDecimal.ROUND_FLOOR); //1.34
new BigDecimal("-1.345").setScale(2, BigDecimal.ROUND_FLOOR); //-1.35
new BigDecimal("-1.346").setScale(2, BigDecimal.ROUND_FLOOR); //-1.35

BigDecimal.ROUND_HALF_UP:四舍五入(和正负无关)

//四舍五入(和正负无关)
new BigDecimal("1.345").setScale(2, BigDecimal.ROUND_HALF_UP); //1.35
new BigDecimal("1.346").setScale(2, BigDecimal.ROUND_HALF_UP); //1.35
new BigDecimal("-1.345").setScale(2, BigDecimal.ROUND_HALF_UP); //-1.35
new BigDecimal("-1.346").setScale(2, BigDecimal.ROUND_HALF_UP); //-1.35

BigDecimal.ROUND_HALF_DOWN:五舍六入(和正负无关)

//五舍六入(和正负无关)
new BigDecimal("1.345").setScale(2, BigDecimal.ROUND_HALF_DOWN); //1.34
new BigDecimal("1.346").setScale(2, BigDecimal.ROUND_HALF_DOWN); //1.35
new BigDecimal("-1.345").setScale(2, BigDecimal.ROUND_HALF_DOWN); //-1.34
new BigDecimal("-1.346").setScale(2, BigDecimal.ROUND_HALF_DOWN); //-1.35

BigDecimal.ROUND_HALF_EVEN:左边奇数四舍五入,左边偶数五舍六入

//左边奇数四舍五入,左边偶数五舍六入
//当在一系列计算中重复应用时,该模式可将累积误差最小化
new BigDecimal("1.345").setScale(2, BigDecimal.ROUND_HALF_EVEN); //1.34
new BigDecimal("1.346").setScale(2, BigDecimal.ROUND_HALF_EVEN); //1.35
new BigDecimal("-1.345").setScale(2, BigDecimal.ROUND_HALF_EVEN); //-1.34
new BigDecimal("-1.346").setScale(2, BigDecimal.ROUND_HALF_EVEN); //1.35
new BigDecimal("1.355").setScale(2, BigDecimal.ROUND_HALF_EVEN); //1.36
new BigDecimal("1.356").setScale(2, BigDecimal.ROUND_HALF_EVEN); //1.36
new BigDecimal("-1.355").setScale(2, BigDecimal.ROUND_HALF_EVEN); //-1.36
new BigDecimal("-1.356").setScale(2, BigDecimal.ROUND_HALF_EVEN); //-1.36

注意:

  1. 使用 new BigDecimal 的字符串构建,不要用 doubel 类型,doule 类型用 BigDecimal.valueOf() 构建。

BigDecimal 格式化

toString 等方法

通常 stripTrailingZerostoPlainString 一起连用。

BigDecimal.valueOf(12.3 * 1000000).toEngineeringString()); //12.3E+6
BigDecimal.valueOf(12.3 * 1000000).toString());  //1.23E+7
BigDecimal.valueOf(12.3 * 1000000).toPlainString()); //12300000

new BigDecimal("1.300").stripTrailingZeros();  //1.3

注意:

  1. 科学计数法返回结果可能不是自己想要的,建议使用下文的 DecimalFormat

DecimalFormat

DecimalFormat 可以提供更灵活的写法。

#:表示只要有可能就把数字拉上这个位置

import java.text.DecimalFormat;
new DecimalFormat("#.####").format(12340);  //12340
new DecimalFormat("#.####").format(1.23);  //1.23
new DecimalFormat("#.####").format(1.2323423);  //1.2323

0:表示如果位数不足则以 0 补充

new DecimalFormat("#.0000").format(12340);  //12340.0000
new DecimalFormat("#.0000").format(1.23);  //1.2300

E:科学计数

new DecimalFormat("#.####E0").format(0.00000234234);  //2.3423E-6
new DecimalFormat("#.####E0").format(132459999);  //1.3246E8
new DecimalFormat("#.####E0").format(6);  //6E0

%:百分比

new DecimalFormat("#.####%").format(0.23);  //23%
new DecimalFormat("#.0000%").format(0.23);  //23.0000%

MessageFormat

MessageFormat 也可以用于格式化,且表达式同 DecimalFormat

MessageFormat.format("{0} to {1,number,#.##}", "1.2323", 1.2323); //1.2323 to 1.23

Last modified on 2023-01-28