Java 数字处理

  • Post author:
  • Post category:java


前段时间系统需要对大部分的数字进行处理,于是写了一个封装类。下面是参考网上资料进行的总结。

Java中对数字处理一般有3种方法。

1,数字的格式化一般用DecimalFormat

DecimalFormat 是 NumberFormat 的一个具体子类,用于格式化十进制数字。该类设计有各种功能,使其能够分析和格式化任意语言环境中的数,包括对西方语言、阿拉伯语和印度语数字的支持。它还支持不同类型的数,包括整数 (123)、定点数 (123.4)、科学记数法表示的数 (1.23E4)、百分数 (12%) 和金额 ($123)。所有这些内容都可以本地化。

DecimalFormat 包含一个模式 和一组符号

符号含义:

符号


位置


本地化?


含义

0


数字





阿拉伯数字

#


数字字





阿拉伯数字,如果不存在则显示为空

.


数字





小数分隔符或货币小数分隔符




数字





减号

,


数字





分组分隔符

E


数字





分隔科学计数法中的尾数和指数。在前缀或后缀中无需加引号。

;


子模式边界





分隔正数和负数子模式

%


前缀或后缀





乘以 100 并显示为百分数

/u2030


前缀或后缀





乘以 1000 并显示为千分数

¤(/u00A4)


前缀或后缀





货币记号,由货币符号替换。如果两个同时出现,则用国际货币符号替换。如果出现在某个模式中,则使用货币小数分隔符,而不使用小数分隔符。




前缀或后缀





用于在前缀或或后缀中为特殊字符加引号,例如 “‘#’#” 将 123 格式化为 “#123″。要创建单引号本身,请连续使用两个单引号:”# o”clock”。

例子:

DecimalFormat df1 = new DecimalFormat(“0.0”);

DecimalFormat df2 = new DecimalFormat(“#.#”);

DecimalFormat df3 = new DecimalFormat(“000.000”);

DecimalFormat df4 = new DecimalFormat(“###.###”);

System.out.println(df1.format(12.34));

System.out.println(df2.format(12.34));

System.out.println(df3.format(12.34));

System.out.println(df4.format(12.34));

运行结果:

12.3

12.3

012.340

12.34

DecimalFormat format = new DecimalFormat(“###,####.000”);

System.out.println(format.format(111111123456.1227222));

Locale.setDefault(Locale.US);

DecimalFormat usFormat = new DecimalFormat(“###,###.000”);

System.out.println(usFormat.format(111111123456.1227222));

DecimalFormat addPattenFormat = new DecimalFormat();

addPattenFormat.applyPattern(“##,###.000”);

System.out.println(addPattenFormat.format(111111123456.1227));

DecimalFormat zhiFormat = new DecimalFormat();

zhiFormat.applyPattern(“0.000E0000”);

System.out.println(zhiFormat.format(10000));

System.out.println(zhiFormat.format(12345678.345));

DecimalFormat percentFormat = new DecimalFormat();

percentFormat.applyPattern(“#0.000%”);

System.out.println(percentFormat.format(0.3052222));

运行结果 :

1111,1112,3456.123

111,111,123,456.123

111,111,123,456.123

1.000E0004

1.235E0007

30.522%

如果使用具有多个分组字符的模式,则最后一个分隔符和整数结尾之间的间隔才是使用的分组大小。所以 “#,##,###,####” == “######,####” == “##,####,####”。

2,对数字精度要求比较高,一般用BigDecimal

Java在java.math包中提供的API类BigDecimal,用来对超过16位有效位的数进行精确的运算。双精度浮点型变量double可以处理16位有效数,但在实际应用中,可能需要对更大或者更小的数进行运算和处理。一般情况下,对于那些不需要准确计算精度的数字,我们可以直接使用Float和Double处理,但是Double.valueOf(String) 和Float.valueOf(String)会丢失精度。所以开发中,如果我们需要精确计算的结果,则必须使用BigDecimal类来操作。

(1)加减乘除

BigDecimal m1 = new BigDecimal(12);

BigDecimal m2 = new BigDecimal(5);

// 加

System.out.println(m1.add(m2));// 17

// 减

System.out.println(m1.subtract(m2));// 7

// 乘

System.out.println(m1.multiply(m2));// 60

// 除

System.out.println(m1.divide(m2, 2,BigDecimal.ROUND_HALF_UP));//2.40

(2)进度取舍

BigDecimal actualValue = new BigDecimal(StringUtil.isNotEmpty(wipRecipeDataVO.getActualValue()) ?



wipRecipeDataVO.getActualValue() : StringUtil.defaultString(wipRecipeDataVO.getValue()));

if(wipRecipeDataVO.getPrecision().length()==1) {

//四舍五入



actualValue = actualValue.setScale(Integer.parseInt(wipRecipeDataVO.getPrecision()), BigDecimal.ROUND_HALF_UP);

}else if(wipRecipeDataVO.getPrecision().startsWith(“/”)) {



//截取



actualValue = actualValue.setScale(Integer.parseInt(StringUtils.substringAfter(wipRecipeDataVO.getPrecision(),”/”)), BigDecimal.ROUND_DOWN);

}else if(wipRecipeDataVO.getPrecision().startsWith(“+”)) {



向上取舍



actualValue = actualValue.setScale(Integer.parseInt(StringUtils.substringAfter(wipRecipeDataVO.getPrecision(),”+”)), BigDecimal.ROUND_CEILING);

}else {



throw new BusinessException(“ERR-5027”, new Object[] {wipRecipeDataVO.getWipEntityId().toString(),



wipRecipeDataVO.getName(), wipRecipeDataVO.getPrecision()});

}

参数定义

ROUND_CEILING

Rounding mode to round towards positive infinity.

向正无穷方向舍入

ROUND_DOWN

Rounding mode to round towards zero.

向零方向舍入

ROUND_FLOOR

Rounding mode to round towards negative infinity.

向负无穷方向舍入

ROUND_HALF_DOWN

Rounding mode to round towards “nearest neighbor” unless both neighbors are equidistant, in which case round down.

向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,向下舍入, 例如1.55 保留一位小数结果为1.5

ROUND_HALF_EVEN

Rounding mode to round towards the “nearest neighbor” unless both neighbors are equidistant, in which case, round towards the even neighbor.

向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,如果保留位数是奇数,使用ROUND_HALF_UP ,如果是偶数,使用ROUND_HALF_DOWN

ROUND_HALF_UP

Rounding mode to round towards “nearest neighbor” unless both neighbors are equidistant, in which case round up.

向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,向上舍入, 1.55保留一位小数结果为1.6

ROUND_UNNECESSARY

Rounding mode to assert that the requested operation has an exact result, hence no rounding is necessary.

计算结果是精确的,不需要舍入模式

ROUND_UP

Rounding mode to round away from zero.

向远离0的方向舍入

3,处理对数字精度要求不高的用Math

Math.ceil()执行向上舍入,即它总是将数值向上舍入为最接近的整数;

Math.floor()执行向下舍入,即它总是将数值向下舍入为最接近的整数;

Math.round()执行标准舍入,即它总是将数值四舍五入为最接近的整数(这也是我们在数学课上学到的舍入规则)。

// Math.ceil(Double a)返回大于等于(>=a)的最大整数

System.out.println(Math.ceil(1.3));// 2.0

// Math.floor(Double a)返回小于等于(<=a)的最大整数

System.out.println(Math.floor(1.3));// 1.0

// Math.rint(Double a)返回离a最近的整数,如果同为整数且同样接近则取偶数

System.out.println(Math.rint(0.5));// 0.0

System.out.println(Math.rint(1.5));// 2.0

System.out.println(Math.rint(0.3));// 0.0

// Math.round(Double a)将参数(a+0.5)之后向下取整整数,

System.out.println(Math.round(1.4));// 1 加上0.5之后变成1.9向下取整等于1

System.out.println(Math.round(1.5));// 1 加上0.5之后变成2向下取整等于2

System.out.println(Math.round(1.6));// 2 加上0.5之后变成2.1向下取整等于2

System.out.println(Math.round(-1.4));// -1 加上0.5之后变成-0.9向下取整等于-1

System.out.println(Math.round(-1.5));// -1 加上0.5之后变成-1向下取整等于-1

System.out.println(Math.round(-1.6));// -2 加上0.5之后变成-1.1向下取整等于-2

// Math.max()取最大值

System.out.println(Math.max(1, 2));// 2

// Math.min()取最小值

System.out.println(Math.min(1, 2));// 2

// Math.abs()取绝对值

System.out.println(Math.abs(-100));// 100

// Math.random()产生0~1之间的double型数字

System.out.println(Math.random());// 结果等于(0<=Math.random()<1.0)



版权声明:本文为qq_35498454原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。