-
Notifications
You must be signed in to change notification settings - Fork 1
DoubleMath
Class provides static utility methods to perform simple numerical operations on double value. For example, direct double comparison is not safe, so double values need to be compared with a delta. This class provides methods for common check and compare operations.
Rounding error is inherent in floating-point computation
Doubles cannot be compared directly. Common solution is to use epsilon (delta) to compare two doubles with some acceptable difference. This class calculates this epsilon dynamically based on the number of digits before decimal point.
Class contains a constant named MAXIMUM_DEFAULT_DECIMALS
. This number represents maximum digits after the decimal point, considered as significant - currently it's 14
. Any number less than 10.0
is significant up to the 14th digit after the point, so number 1.2
will be rounded to the 14th decimal, and number 0.00012
will also be rounded to the 14th decimal. But with each digit added before decimal point - one significant digit will be cut from the end. So number 10.2
will be rounded to the 13th digit after the point, and number 365.12
will be rounded to the 12th digit after the point. Any number with more than 14 digits before decimal point will be rounded to the 0th decimal (to the integer value).
So the basic idea is that only first 15
total digits of a number are significant for any x
where |x| < 1e15
. As a result lowest processable number is 1e-14
, for #round(1e-15)
returns 0.0
.
Method #getLastAffectedDecimal(double)
might be used to find out number of significant digits after decimal point.
=====
- isZero(Double)
- isPositive(Double)
- isNegative(Double)
- isFinite(Double)
- isNumber(Double)
- equals(Double, Double)
- equals(Double, Double, double)
These are null-safe methods. None of them will ever throw an NPE for any specified value. So for example #isZero
returns true
if specified object is not null and equal to 0.0
according to the #equals
method. And method #equals
returns true
if specified objects are either both nulls, or both non-nulls and equal to the last signigicant decimal.
=====
- compare(double, double)
- compare(double, double, double)
Second method accepts epsilon (comparison delta) as third argument, which takes all responsibility off the class itself for the accuracy of the comparison.
These methods are not made to accept nulls, for comparing a null
value to a non-null
value is a kind of operation caller should take care of himself, for there's a question open - shall nulls be first, or last. And such a behavior is too specific and not interesting in the scope of DoubleMath
.
=====
- roundTo(double, int)
- round(double)
First method performs rounding to the specified digit after decimal point. For example #roundTo(2.345, 2)
will return 2.35
, and #roundTo(2.345, 1)
will return 2.3
. There's a constant field MAXIMUM_POSSIBLE_DECIMALS
that represents maximum value of the int
specified into this method.
Second method round specified number to the last significant digit, according to the #getLastAffectedDecimal
method. Which is useful to get rid of a "rounding error tail". For example, operation 0.7 + 0.1
will return 0.7999999999999999
as a result, but round(0.7 + 0.1)
will return 0.8
.
These methods don't accept nulls, for it's callers business to think, how exactly to round a null
.