Why is Math.Round(0.125, 2) rounding to 0.12?
Dim foo As Decimal
foo = Math.Round(0.125, 2)
foo is now 0.12 but it should b 0.13
I heard it's because some standard in .Net rounds to the nearest even number, but that's just bad math. 12.5 will round down to 12, but 13.5 will round up to 14. Is there a way to fix this?
The main reason to use the round-to-even method is to avoid systematic bias when calculating with rounded numbers. One application involves mental arithmetic. If you want to estimate the sum (or mean) of a list of numbers, you can mentally round the numbers to the nearest integer and add up the numbers in your head.
Round With no options, we use just one argument. This rounds the number to 123. And With a second argument of 1, we round to one decimal place. This yields the values 123.5 (for AwayFromZero) and 123.4 (for ToEven).
The Math. round() method rounds a number to the nearest integer. 2.49 will be rounded down (2), and 2.5 will be rounded up (3).
Since, 2.5 being the decimal number, it is not considered to be a whole number. However, it can be converted to a whole number by rounding it off to the nearest whole number. 2.5 rounded off to the nearest whole number is 3. Hence, the whole number of 2.5 will be 3.
From the documentation on the Math.Round(decimal)
method:
If the fractional component of d is halfway between two integers, one of which is even and the other odd, the even number is returned.
The same logic applies to the Math.Round(decimal, int)
overload. Notice:
Math.Round(0.125, 2) // 0.12
Math.Round(0.135, 2) // 0.14
Math.Round(0.145, 2) // 0.14
It's not 'bad math'; it's a common rounding strategy known as 'round-to-even'. From Wikipedia:
This variant of the round-to-nearest method is also called unbiased rounding, convergent rounding, statistician's rounding, Dutch rounding, Gaussian rounding, odd-even rounding, bankers' rounding or broken rounding, and is widely used in bookkeeping.
This is the default rounding mode used in IEEE 754 computing functions and operators.
If you want finer control over how it rounds, you can specify a MidpointRounding
parameter
Math.Round(0.125, 2, MidpointRounding.AwayFromZero) // 0.13
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With