General Utility Library for C++14
2.12
|
Numerical utility functions.
Functions | |
template<typename ValueT > | |
constexpr auto | gul14::abs (ValueT n) noexcept -> std::enable_if_t< std::is_unsigned< ValueT >::value, ValueT > |
Compute the absolute value of a number. More... | |
template<typename NumT , typename OrderT , typename = std::enable_if_t< std::is_arithmetic<NumT>::value and std::is_arithmetic<OrderT>::value >> | |
bool | gul14::within_orders (const NumT a, const NumT b, const OrderT orders) noexcept(false) |
Determine if two numbers are almost equal, comparing only some significant digits. More... | |
template<typename NumT > | |
bool | gul14::within_abs (NumT a, NumT b, NumT tol) noexcept |
Determine if two numbers are almost equal, allowing for an absolute difference. More... | |
template<typename NumT , typename = std::enable_if_t<std::is_floating_point<NumT>::value>> | |
bool | gul14::within_ulp (NumT a, NumT b, unsigned int ulp) |
Determine if two numbers are almost equal, allowing for a difference of a given number of units-in-the-last-place (ULPs). More... | |
template<class NumT > | |
constexpr const NumT & | gul14::clamp (const NumT &v, const NumT &lo, const NumT &hi) |
Coerce a value to be within a given range. More... | |
template<class NumT , class Compare > | |
constexpr const NumT & | gul14::clamp (const NumT &v, const NumT &lo, const NumT &hi, Compare comp) |
This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts. More... | |
|
constexprnoexcept |
Compute the absolute value of a number.
This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.
This function is almost equal to std::abs() with the exception of unsigned integral types, which are returned unchanged and in their original type. This is especially useful in templates, where std::abs() cannot be used for all arithmetic types.
n | The number whose absolute value should be determined. |
Referenced by gul14::gcd(), gul14::lcm(), gul14::remove_outliers(), gul14::within_abs(), gul14::within_orders(), and gul14::within_ulp().
|
constexpr |
Coerce a value to be within a given range.
Check if value v
is between (including) lo
and hi
. If it is too low, lo
is returned. If it is too high, hi
is returned.
lo
must not be greater than hi
, but they are allowed to be equal.
Only operator<()
is used for this, so it has to be defined for NumT
.
Note that all parameters need to be of the same type. Add the correct suffix if using a literal as shown in the following example:
NumT | Type of the objects to compare. Needs to have operator<() defined. |
v | The value to clamp |
lo | The lower boundary to clamp v to |
hi | The upper boundary to clamp v to |
lo
if v
is less than lo
, a reference to hi
if hi
is less than v
, or a reference to v
otherwise.
|
constexpr |
This is an overloaded member function, provided for convenience. It differs from the above function only in what argument(s) it accepts.
NumT | Type of the objects to compare. Needs to have operator<() defined. |
Compare | Type of the comparison function. See notes below. |
v | The value to clamp |
lo | The lower boundary to clamp v to |
hi | The upper boundary to clamp v to |
comp | Comparison function object which returns true if the first argument is less than the second. |
The signature of the comparison function should be equivalent to the following:
While the signature does not explicitly require passing the arguments by const reference, the function must not modify the objects passed to it and must be able to accept all values of type (possibly const) Type1
and Type2
regardless of value category. This means that neither Type1 &
nor Type1
are allowed unless a move is equivalent to a copy for Type1
. The types Type1
and Type2
must be such that an object of type T
can be implicitly converted to both of them.
|
noexcept |
Determine if two numbers are almost equal, allowing for an absolute difference.
All arguments must be the same numeric type (floating point or integer).
a | The first number to compare |
b | The second number to compare |
tol | The absolute tolerance |
References gul14::abs().
|
noexcept |
Determine if two numbers are almost equal, comparing only some significant digits.
The functions compares the specified number of significant decimal digits of the two values and returns true if they are equal within these digits.
a = 23736384; b = 23736228; within_orders(a, b, 5) => true (first 5 digits equal) a = 23736384; b = 23735384; within_orders(a, b, 5) => false (digit #5 differs)
Unexpected behavior can result when orders is low (< 3) as the simple concept of orders equals digits does not hold so strict anymore.
Remember that any nonzero number has infinite different significant digits compared with 0.00000000. So if one operand is 0.0 while the other is not 0.0 the result must be false.
a | The first number to compare |
b | The second number to compare (same type as a ) |
orders | The number of digits to take for comparison (any numeric type) |
a
and b
are equal or the difference between a
and b
is orders
orders of magnitude lower than the value of a
or b
References gul14::abs(), and gul14::maximum().
bool gul14::within_ulp | ( | NumT | a, |
NumT | b, | ||
unsigned int | ulp | ||
) |
Determine if two numbers are almost equal, allowing for a difference of a given number of units-in-the-last-place (ULPs).
One ULP is the spacing between two consecutive floating point representations. There are no possible values in between. Roughly speaking, one ULP is for floating point numbers what the 1 is for integral numbers.
All arguments must be of the same floating point type.
a | The first number to compare |
b | The second number to compare |
ulp | Allowed number of floating point steps in between |
References gul14::abs().