Math.rint()
和Math.round()
有什么区别?
Math.rint()
和Math.round()
有什么区别?
Math.rint()
和Math.round()
有几个不同之处,但可能对Java应用程序的业务逻辑影响最大的是它们处理位于边界上的整数的舍入方式(例如4.5
位于4
和5
的边界上)。请考虑以下代码片段和输出:
double val1 = 4.2;
double val2 = 4.5;
System.out.println("Math.rint(" + val1 + ") = " + Math.rint(val1));
System.out.println("Math.round(" + val1 + ") = " + Math.round(val1));
System.out.println("Math.rint(" + val2 + ") = " + Math.rint(val2));
System.out.println("Math.round(" + val2 + ") = " + Math.round(val2));
System.out.println("Math.rint(" + (val2 + 0.001d) + ") = " + Math.rint(val2 + 0.001d));
System.out.println("Math.round(" + (val2 + 0.001d) + ") = " + Math.round(val2 + 0.001d));
输出:
Math.rint(4.2) = 4.0
Math.round(4.2) = 4
Math.rint(4.5) = 4.0
Math.round(4.5) = 5
Math.rint(5.5) = 6.0
Math.round(5.5) = 6
Math.rint(4.501) = 5.0
Math.round(4.501) = 5
如您所见,Math.rint(4.5)
实际上将其转换为最近的偶数整数,而 Math.round(4.5)
则会向上舍入,并且这值得指出。但是,在所有其他情况下,它们都表现出我们所期望的相同的舍入规则。
这里有一篇有用的 Code Ranch 文章,简要比较了 Math.rint()
和 Math.round()
:http://www.coderanch.com/t/239803/java-programmer-OCPJP/certification/Difference-rint-methods-Math-class
round
和rint
都会将数字四舍五入到最接近的整数。当数字恰好处于两个整数中间时,前者会向上舍入(到正无穷),而后者会舍入为偶数。注意:通过使用rint
进行偶数舍入,我们可以在计算一组数字的平均值时避免统计偏差。 - rosshjbMath.rint()示例: 2.50位于2.00和3.00之间。 Math.rint()返回最接近的偶数double值。 Math.rint(2.50)返回2.0。
Math.round()示例: 2.50位于2.00和3.00之间。 Math.round()返回最接近的较高整数。 Math.round(2.50)返回3
有一种类型的返回值差异:
Math.round()
返回 long
或 int
Math.rint()
返回 double
但关键的区别在于对0.5
处数值的处理。
Math.round()
将 9.5 <= x < 10.5
转换为 10
Math.rint()
将 9.5 <= x <= 10.5
转换为 10.0
Math.round()
将 10.5 <= x < 11.5
转换为 11
Math.rint()
将 10.5 < x < 11.5
转换为 11.0
Math.round()
将 11.5 <= x < 12.5
转换为 12
Math.rint()
将 11.5 <= x <= 12.5
转换为 12.0
(注意不等式!) 因此,Math.round()
总是在中点(0.5)向上舍入:文档。
相反,Math.rint()
偏向于中点最接近的偶数:文档。
例如,尝试运行以下简单示例:
public class HelloWorld{
public static void main(String []args){
System.out.println("Math.round() of 9.5 is " + Math.round(9.5));
System.out.println("Math.round() of 10.5 is " + Math.round(10.5));
System.out.println("Math.round() of 11.5 is " + Math.round(11.5));
System.out.println("Math.round() of 12.5 is " + Math.round(12.5));
System.out.println("Math.rint() of 9.5 is " + Math.rint(9.5));
System.out.println("Math.rint() of 10.5 is " + Math.rint(10.5));
System.out.println("Math.rint() of 11.5 is " + Math.rint(11.5));
System.out.println("Math.rint() of 12.5 is " + Math.rint(12.5));
}
}
.5
结尾的参数、 signed 0
、 NaN
或Infinity
时,它们的行为会有所不同。
Math.round
接受double
和float
,但由于一些原因返回类型不同(分别是long
和int
,这是能覆盖整个参数范围的最小类型)。
Math.rint
接受double
并返回double
。与Math.round
相比,它更少“破坏”值,因为在几种情况下它不会改变值(见下文)。
(来自C#中Jon Skeet的答案。 Math.Round在C#中的行为更类似于Java中的此方法的行为遵循IEEE Standard 754第4节。这种取整有时被称为“四舍五入”,或者银行家舍入法。它最小化了由于始终朝一个方向舍入中点值而导致的舍入误差。
Math.rint
,尽管可能很令人困惑。)
static double rint(double a)
Returns the double value that is closest in value to the argument and is equal to a mathematical integer.
Returns the double value that is closest in value to the argument and is equal to a mathematical integer. If two double values that are mathematical integers are equally close, the result is the integer value that is even.
Special cases:
If the argument value is already equal to a mathematical integer, then the result is the same as the argument.
If the argument is NaN or an infinity or positive zero or negative zero, then the result is the same as the argument.
...
static long round(double a)
...
static int round(float a)
Returns the closest int to the argument, with ties rounding up.
Special cases:
- If the argument is NaN, the result is 0.
- If the argument is negative infinity or any value less than or equal to the value of Integer.MIN_VALUE, the result is equal to the value of Integer.MIN_VALUE.
- If the argument is positive infinity or any value greater than or equal to the value of Integer.MAX_VALUE, the result is equal to the value of Integer.MAX_VALUE.
您还可以通过RoundingMode更改Math.round
的行为:
public enum RoundingMode extends Enum<RoundingMode>
Specifies a rounding behavior for numerical operations capable of discarding precision. Each rounding mode indicates how the least significant returned digit of a rounded result is to be calculated. If fewer digits are returned than the digits needed to represent the exact numerical result, the discarded digits will be referred to as the discarded fraction regardless the digits' contribution to the value of the number. In other words, considered as a numerical value, the discarded fraction could have an absolute value greater than one.
Each rounding mode description includes a table listing how different two-digit decimal values would round to a one digit decimal value under the rounding mode in question. The result column in the tables could be gotten by creating a BigDecimal number with the specified value, forming a MathContext object with the proper settings (precision set to 1, and the roundingMode set to the rounding mode in question), and calling round on this number with the proper MathContext. A summary table showing the results of these rounding operations for all rounding modes appears below.
Result of rounding input to one digit with the given rounding
Input UP DOWN CEILING FLOOR HALF_UP HALF_DOWN HALF_EVEN UNNECESSARY 5.5 6 5 6 5 6 5 6 throw ArithmeticException 2.5 3 2 3 2 3 2 2 throw ArithmeticException 1.6 2 1 2 1 2 2 2 throw ArithmeticException 1.1 2 1 2 1 1 1 1 throw ArithmeticException 1.0 1 1 1 1 1 1 1 1 -1.0 -1 -1 -1 -1 -1 -1 -1 -1 -1.1 -2 -1 -1 -2 -1 -1 -1 throw ArithmeticException -1.6 -2 -1 -1 -2 -2 -2 -2 throw ArithmeticException -2.5 -3 -2 -2 -3 -3 -2 -2 throw ArithmeticException -5.5 -6 -5 -5 -6 -6 -5 -6 throw ArithmeticException
Math.round()
将 [10.5, 11.5[
转换为 11。Math.rint()
将 ]10.5, 11.5[
转换为 11.0。Math.round()
返回 long 或 int。Math.rint()
返回 double。Math.round()
更偏向于使用中点(0.5)来取较高的值。对于正数:
如果小数部分在0(包括)和0.5(不包括)之间,则round()返回该数字的整数部分。
如果小数部分在0.5(包括)和1(不包括)之间,则round()返回该数字的整数部分+1。
但是在rint的情况下,
如果小数部分在0(包括)和0.5(包括)之间,则rint()返回该数字的整数部分。
如果小数部分在0.5(不包括)和1(不包括)之间,则round()返回该数字的整数部分+1。
对于负数:
两者的行为相同,即
如果小数部分在0(包括)和0.5(包括)之间,则返回该数字的整数部分。
如果小数部分在0.5(包括)和1(不包括)之间,则返回该数字的整数部分-1。
小数部分只是小数点后面的部分