Java核心类(4 - BigInteger和BigDecimal)
BigInteger
在Java中,由CPU原生提供的整型最大范围是64位long
型整数。使用long
型数据可以直接通过CPU指令进行计算,速度非常快。
如果我们使用的整数范围超过了long
,那么我们就只能使用软件模拟一个大整数。java.math.BigInteger
就是用来表示任意大小的整数。BigInteger
内部用一个int[]
数组来模拟一个非常大的整数:
import java.math.BigInteger;
public class Main {
public static void main(String[] args) {
BigInteger big = new BigInteger("123456789");
System.out.println(big.pow(5));
}
}
输出:
28679718602997181072337614380936720482949
对BigInteger
做运算时,只能使用实例方法,常用的运算方法如下:
- 加法:
BigInteger add(BigInteger val)
返回两个大整数的和 - 减法:
BigInteger subtract(BigInteger val)
返回两个大整数相减的结果 - 乘法:
BigInteger multiply(BigInteger val)
返回两个大整数的乘积 - 除法:
BigInteger divide(BigInteger val)
返回两个大整数的商 - 取模:
BigInteger mod(BigInteger val)
用当前大整数对val取模 - 求相反数:
BigInteger negate()
返回当前大整数的相反数 - 幂运算:
BigInteger pow(int exponent)
返回当前大整数的exponent次方
数值转换方法如下:
- 转换为
byte
:byteValue()
- 转换为
short
:shortValue()
- 转换为
int
:intValue()
- 转换为
long
:longValue()
- 转换为
float
:floatValue()
- 转换为
double
:doubleValue()
通过上述方法,可以把BigInteger
转换为基本类型。但是,如果BigInteger
表示的范围超过了基本数据范围,转换时将丢失高位信息,即结果不一定是准确的。如果需要准确的转换成基本数据类型,可以使用intValueExact()
、longValueExact
等方法,在转换时如果超出范围,将直接抛出ArithmeticException
异常。
BigDecimal
和BigInteger类似,BigDecimal
可以表示一个任意大小且精度完全准确的浮点数。
构造方法:
BigDecimal(String val)
:将String
类型转换成BigDecimal
类型BigDecimal(double val)
:将double
类型转换成BigDecimal
类型BigDecimal(int val)
:将int
类型转换成BigDecimal
类型BigDecimal(long val)
:将long
类型转换成BigDecimal
类型
数值转换
- 转换成
String
:toString()
- 转换成
double
:doubleValue()
- 转换成
float
:floatValue()
- 转换成
long
:longValue()
- 转换成
int
:intValue()
运算方法:
- 加法:
BigDecimal add(BigDecimal val)
返回两个BigDecimal
的和; - 减法:
BigDecimal subtract(BigDecimal val)
返回两个BigDecimal
的差; - 乘法:
BigDecimal multiply(BigDecimal val)
返回两个BigDecimal
的乘积; - 除法:
BigDecimal divide(BigDecimal divisor)
返回两个BigDecimal
的商; - 取模:
BigDecimal remainder(BigDecimal divisor)
返回两个BigDecimal
的和; - 最大数:
BigDecimal max(BigDecimal val)
返回两个BigDecimal
的最大值; - 最小数:
BigDecimal min(BigDecimal val)
返回两个BigDecimal
的最小值; - 绝对值:
BigDecimal abs()
返回BigDecimal
的绝对值; - 相反数:
BigDecimal negate()
返回BigDecimal
的相反数;
其中除法运算较为特殊:
BigDecimal divide(BigDecimal divisor, int scale, int roundingMode)
可以看出,除法divide
有三个参数的方法,第一参数divisor
表示除数,第二参数scale
表示小数点后保留位数,第三个参数表示取舍规则。只有在作除法运算或者四舍五入时才用到取舍规则。
取舍规则如下:
ROUND_CEILING //向正无穷方向舍入
ROUND_DOWN //向零方向舍入
ROUND_FLOOR //向负无穷方向舍入
ROUND_HALF_DOWN //向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,向下舍入, 例如1.55 保留一位小数结果为1.5
ROUND_HALF_EVEN //向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,如果保留位数是奇数,使用ROUND_HALF_UP,如果是偶数,使用ROUND_HALF_DOWN
ROUND_HALF_UP //向(距离)最近的一边舍入,除非两边(的距离)是相等,如果是这样,向上舍入, 1.55保留一位小数结果为1.6
ROUND_UNNECESSARY //计算结果是精确的,不需要舍入模式
ROUND_UP //向远离0的方向舍入
我们最常用的四舍五入是ROUND_HALF_UP
四舍五入
setScale(,int scale, int roundingMode)
第一个参数表示小数点后保留位数,第二个参数表示取舍规则,最常用的四舍五入是HALF_UP
。
比较BigDecimal
可以使用equals()
方法,但是要求两个Bigdecimal
的值相等,并且要求他们的位数scale()
相等。比如:
BigDecimal a = new BigDecimal("123.32000");
BigDecimal b = new BigDecimal("123.32");
System.out.println(a.equals(b)); // false
必须使用compareTo()
方法来比较,它会根据两个值的大小分别返回负数、正数和0,分别代表小于、大于和等于。
BigDecimal a = new BigDecimal("123.32000");
BigDecimal b = new BigDecimal("123.32");
System.out.println(a.compareTo(b)); // 0
其他方法:
stripTrailingZeros()
:可以将一个BigDecimal
格式化为一个相等的但是去掉了末尾0的BigDecimal
scale()
:表示小数位数,如果为负数,比如-2
,表示这个数是整数,且末尾有2个0。