8#ifndef META_OCEAN_MATH_NUMERIC_H
9#define META_OCEAN_MATH_NUMERIC_H
26template <
typename T>
class NumericT;
64 static constexpr T
pi();
70 static constexpr T
pi2();
76 static constexpr T
pi_2();
82 static constexpr T
pi_3();
88 static constexpr T
pi_4();
112 static constexpr T
e();
133 static inline T
abs(
const T value);
149 static constexpr inline T
sqr(
const T value);
157 static inline T
sum(
const T* values,
const size_t number);
165 static inline T
summedSqr(
const T* values,
const size_t number);
173 static constexpr inline T
sqrDistance(
const T value0,
const T value1);
180 static inline T
sqrt(
const T value);
187 static inline std::complex<T>
sqrt(
const std::complex<T>& value);
194 static inline T
sin(
const T value);
201 static inline T
cos(
const T value);
208 static inline T
tan(
const T value);
215 static inline T
asin(
const T value);
222 static inline T
acos(
const T value);
229 static inline T
atan(
const T value);
237 static inline T
atan2(
const T y,
const T x);
244 static inline T
exp(
const T value);
251 static inline T
log(
const T value);
259 static inline T
log1p(
const T value);
266 static inline T
log2(
const T value);
273 static inline T
log10(
const T value);
281 static inline T
fmod(
const T valueA,
const T valueB);
290 static inline T
dot(
const T* vectorA,
const T* vectorB,
const size_t size);
319 static inline bool angleIsEqual(
const T angleA,
const T angleB);
336 static inline bool angleIsEqual(
const T angleA,
const T angleB,
const T epsilon);
353 static inline T
angleDistance(
const T angleA,
const T angleB);
361 static inline T
pow(
const T x,
const T y);
369 static inline std::complex<T>
pow(
const std::complex<T>& x,
const T y);
377 static constexpr T
integerPow(
const T x,
const unsigned int y);
384 static constexpr inline T
factorial(
const T& value);
400 static inline T
ceil(
const T value);
407 static inline T
floor(
const T value);
425 static constexpr inline int32_t
round32(
const T value);
443 static constexpr inline int64_t
round64(
const T value);
452 static constexpr inline T
ratio(
const T nominator,
const T denominator,
const T fallback = T(1));
459 static constexpr inline bool isEqualEps(
const T value);
466 static constexpr inline bool isEqualEps(
const std::complex<T>& value);
480 static constexpr inline bool isWeakEqualEps(
const std::complex<T>& value);
494 static constexpr inline bool isNotEqualEps(
const std::complex<T>& value);
516 static inline bool isEqual(
const T first,
const T second);
524 static inline bool isEqual(
const std::complex<T>& first,
const std::complex<T>& second);
532 static inline bool isWeakEqual(
const T first,
const T second);
540 static inline bool isWeakEqual(
const std::complex<T>& first,
const std::complex<T>& second);
549 static inline bool isEqual(
const T first,
const T second,
const T epsilon);
558 static inline bool isEqual(
const std::complex<T>& first,
const std::complex<T>& second,
const T epsilon);
571 template <
int tMagnitude>
572 static inline bool isEqual(
const T first,
const T second,
const T referenceEpsilon);
580 static inline bool isNotEqual(
const T first,
const T second);
588 static inline bool isNotEqual(
const std::complex<T>& first,
const std::complex<T>& second);
604 static inline bool isNotWeakEqual(
const std::complex<T>& first,
const std::complex<T>& second);
613 static inline bool isNotEqual(
const T first,
const T second,
const T epsilon);
622 static inline bool isNotEqual(
const std::complex<T>& first,
const std::complex<T>& second,
const T epsilon);
641 static constexpr bool isInsideWeakRange(
const T lower,
const T value,
const T upper);
665 static constexpr T
nan();
672 static inline bool isNan(
const T value);
679 static inline bool isNan(
const std::complex<T>& value);
685 static constexpr T
inf();
693 static inline bool isInf(
const T value);
701 static inline bool isInf(
const std::complex<T>& value);
725 template <
typename TValue>
733 static constexpr inline T
deg2rad(
const T deg);
740 static constexpr inline T
rad2deg(
const T rad);
746 static constexpr inline T
maxValue();
752 static constexpr inline T
minValue();
759 static constexpr inline T
sign(
const T& value);
767 static constexpr inline T
copySign(
const T signReceiver,
const T signProvider);
775 static constexpr inline T
invertSign(
const T signReceiver,
const T signProvider);
842 static inline T
gaussianDistribution2(
const T x,
const T y,
const T x0,
const T y0,
const T sigmaX,
const T sigmaY);
878 static inline T
gaussianDistribution3(
const T x,
const T y,
const T z,
const T sigmaX,
const T sigmaY,
const T sigmaZ);
893 static inline T
gaussianDistribution3(
const T x,
const T y,
const T z,
const T x0,
const T y0,
const T z0,
const T sigmaX,
const T sigmaY,
const T sigmaZ);
922 static inline T
normalizedGaussianDistribution3(
const T x,
const T y,
const T z,
const T x0,
const T y0,
const T z0,
const T sigmaX,
const T sigmaY,
const T sigmaZ);
928 return T(3.1415926535897932384626433832795);
934 return T(6.283185307179586476925286766559);
940 return T(1.5707963267948966192313216916395);
946 return T(1.0471975511965977461542144610932);
952 return T(0.78539816339744830961566084581988);
958 return T(9.8696044010893586188344909998762);
964 return T(39.478417604357434475337963999505);
970 return T(2.4674011002723396547086227499667);
976 return T(2.71828182845904523536);
1219template <
typename T>
1222 return ::abs(value);
1232 ocean_assert(value != std::numeric_limits<signed char>::lowest() &&
"The absolute value of -128 is 128 but then casted to -128");
1234 return (
signed char)(::abs(value));
1254 ocean_assert(value != std::numeric_limits<short>::lowest() &&
"The absolute value of -32768 is 32768 but then casted to -32768");
1256 return short(::abs(value));
1276 ocean_assert(value != std::numeric_limits<int>::lowest());
1278 return ::abs(value);
1298 ocean_assert(value != std::numeric_limits<long>::lowest());
1300 return ::labs(value);
1320 ocean_assert(value != std::numeric_limits<long long>::lowest());
1322 return ::llabs(value);
1352 return fabsf(value);
1355template <
typename T>
1368 return (
unsigned char)(::abs(
int(value)));
1388 return (
unsigned short)::abs(
int(value));
1408 if (value == std::numeric_limits<int>::lowest())
1411 return (
unsigned int)(std::numeric_limits<int>::max()) + 1u;
1414 return (
unsigned int)(::abs(value));
1434 ocean_assert((
unsigned long)::llabs(std::numeric_limits<long>::max()) == (
unsigned long)(-(std::numeric_limits<long>::lowest() + 1l)));
1435 return (
unsigned long)::llabs(value);
1455 if (value == std::numeric_limits<long long>::lowest())
1458 return (
unsigned long long)(std::numeric_limits<long long>::max()) + 1ull;
1461 return (
unsigned long long)(::llabs(value));
1494template <
typename T>
1497 return value * value;
1500template <
typename T>
1505 for (
size_t n = 0; n < number; ++n)
1507 result += values[n];
1513template <
typename T>
1518 for (
size_t n = 0; n < number; ++n)
1520 result +=
sqr(values[n]);
1526template <
typename T>
1529 return sqr(value0 - value1);
1532template <
typename T>
1535 ocean_assert(value >= T(0));
1536 return T(::sqrt(value));
1546 ocean_assert(value >= 0.0f);
1547 return ::sqrtf(value);
1557 ocean_assert(value >= 0);
1558 return int(::sqrtf(
float(value)));
1561template <
typename T>
1564 return std::sqrt<T>(value);
1567template <
typename T>
1570 return ::sin(value);
1583template <
typename T>
1586 return ::cos(value);
1599template <
typename T>
1602 return ::tan(value);
1615template <
typename T>
1618 return ::atan(value);
1628 return atanf(value);
1631template <
typename T>
1636 const T angle = ::atan2(y, x);
1642template <
typename T>
1645 return ::exp(value);
1651 return ::expf(value);
1654template <
typename T>
1657 ocean_assert(value > 0);
1658 return ::log(value);
1664 ocean_assert(value > 0);
1665 return ::logf(value);
1668template <
typename T>
1671 ocean_assert(value > -1);
1672 return ::log1p(value);
1678 ocean_assert(value > -1);
1679 return ::log1pf(value);
1682template <
typename T>
1685 ocean_assert(value > 0);
1687#if (defined(OCEAN_COMPILER_MSC) && OCEAN_MSC_VERSION >= 1800) || (OCEAN_CLANG_VERSION >= 30300 && (!defined(__ANDROID__) || !__ANDROID__))
1688 return ::log2(value);
1690 return ::log(value) * 1.44269504088896340736;
1701 ocean_assert(value > 0);
1703#if (defined(OCEAN_COMPILER_MSC) && OCEAN_MSC_VERSION >= 1800) || (OCEAN_CLANG_VERSION >= 30300 && (!defined(__ANDROID__) || !__ANDROID__))
1704 return ::log2f(value);
1706 return ::logf(value) * 1.44269504088896340736f;
1710template <
typename T>
1713 ocean_assert(value > 0);
1714 return ::log10(value);
1720 ocean_assert(value > 0);
1721 return ::log10f(value);
1731 return atan2f(y, x);
1734template <
typename T>
1737 return ::fmod(valueA, valueB);
1747 return fmodf(valueA, valueB);
1750template <
typename T>
1755 for (
size_t n = 0; n < size; ++n)
1757 result += vectorA[n] * vectorB[n];
1763template <
typename T>
1766 const T adjusted = fmod(angle, pi2());
1770 ocean_assert((std::is_same<T, float>::value) || (pi2() + adjusted >= 0 && pi2() + adjusted < pi2()));
1771 return pi2() + adjusted;
1774 ocean_assert(adjusted >= 0 && adjusted < pi2());
1778template <
typename T>
1781 const T adjusted = fmod(angle, pi());
1785 ocean_assert(pi() + adjusted >= 0 && pi() + adjusted < pi());
1786 return pi() + adjusted;
1789 ocean_assert(adjusted >= 0 && adjusted < pi());
1793template <
typename T>
1796 if (angle > -pi() && angle <= pi())
1801 const T adjusted = fmod(angle, pi2());
1803 if (isAbove(adjusted, pi()))
1805 ocean_assert(adjusted - pi2() > -pi() - eps() && adjusted - pi2() <= pi() + eps());
1806 return adjusted - pi2();
1808 else if (isBelow(adjusted, -pi()))
1810 ocean_assert(adjusted + pi2() > -pi() - eps() && adjusted + pi2() <= pi() + eps());
1811 return adjusted + pi2();
1814 ocean_assert(adjusted > -pi() && adjusted <= pi());
1818template <
typename T>
1821 return isEqualEps(angleDistance(angleA, angleB));
1824template <
typename T>
1827 return isWeakEqualEps(angleDistance(angleA, angleB));
1830template <
typename T>
1833 ocean_assert(epsilon >= T(0));
1834 return isEqual(angleDistance(angleA, angleB), T(0), epsilon);
1837template <
typename T>
1840 ocean_assert(threshold < pi());
1842 return isBelow(abs(angleAdjustNull(angleA - angleB)), threshold);
1845template <
typename T>
1848 const T distance = abs(angleAdjustPositive(angleA) - angleAdjustPositive(angleB));
1859template <
typename T>
1865template <
typename T>
1868 return std::pow<T>(x, y);
1881template <
typename T>
1884 return y == 0u ? T(1) : x * integerPow(x, y - 1u);
1887template <
typename T>
1890 ocean_assert(value >= 0);
1891 ocean_assert(T(int64_t(value)) == value);
1900 for (
unsigned int n = 3u; n <= (
unsigned int)value; ++n)
1902 ocean_assert(maxValue() / T(n) >= result);
1955 ocean_assert(
false &&
"Invalid factorial value!");
1959template <
typename T>
1962 ocean_assert(n >= 0 && k >= 0);
1963 ocean_assert(T(int64_t(n)) == n);
1964 ocean_assert(T(int64_t(k)) == k);
1966 if (n <= T(1) || k == T(0) || n == k)
1971 ocean_assert(k < n);
1973 T result = n - k + T(1);
1975 for (
unsigned int i = (
unsigned int)(n - k) + 2u; i <= (
unsigned int)(n); ++i)
1977 ocean_assert(maxValue() / T(i) >= result);
1981 for (
unsigned int i = 2u; i <= (
unsigned int)(k); ++i)
1983 ocean_assert((result / T(i)) * T(i) == result);
1990template <
typename T>
1993 static_assert(std::is_floating_point<T>::value ==
false,
"Data type must not be a floating point!");
2005 return ::ceilf(value);
2015 return ::ceil(value);
2025 return ::ceill(value);
2028template <
typename T>
2031 static_assert(std::is_floating_point<T>::value ==
false,
"Data type must not be a floating point!");
2043 return ::floorf(value);
2053 return ::floor(value);
2063 return ::floorl(value);
2066template <
typename T>
2069 return int32_t(value + copySign(T(0.5), value));
2072template <
typename T>
2075 return int64_t(value + copySign(T(0.5), value));
2078template <
typename T>
2081 if (isEqualEps(denominator))
2086 return nominator / denominator;
2089template <
typename T>
2092 ocean_assert(isNan(value) ==
false);
2093 ocean_assert((fabs(value) <= eps()) == (-eps() <= value && value <= eps()));
2095 return -eps() <= value && value <= eps();
2101 return value == (
signed char)(0);
2107 return value == (
unsigned char)(0);
2113 return value == short(0);
2119 return value == (
unsigned short)(0);
2143 return value == 0ul;
2149 return value == 0ll;
2155 return value == 0ull;
2158template <
typename T>
2161 return isEqualEps(value.real()) && isEqualEps(value.imag());
2164template <
typename T>
2167 ocean_assert(isNan(value) ==
false);
2168 ocean_assert((fabs(value) <= weakEps()) == (-weakEps() <= value && value <= weakEps()));
2170 return -weakEps() <= value && value <= weakEps();
2176 return value == (
signed char)(0);
2182 return value == (
unsigned char)(0);
2188 return value == short(0);
2194 return value == (
unsigned short)(0);
2218 return value == 0ul;
2224 return value == 0ll;
2230 return value == 0ull;
2233template <
typename T>
2236 return isWeakEqualEps(value.real()) && isWeakEqualEps(value.imag());
2239template <
typename T>
2242 ocean_assert(isNan(value) ==
false);
2243 ocean_assert((fabs(value) > eps()) == (value > eps() || value < -eps()));
2245 return value > eps() || value < -eps();
2251 return value != (
signed char)(0);
2257 return value != (
unsigned char)(0);
2263 return value != short(0);
2269 return value != (
unsigned short)(0);
2293 return value != 0ul;
2299 return value != 0ll;
2305 return value != 0ull;
2308template <
typename T>
2311 return value.real() > eps() || value.real() < -eps() || value.imag() > eps() || value.imag() < -eps();
2314template <
typename T>
2317 ocean_assert((fabs(value) > weakEps()) == (value > weakEps() || value < -weakEps()));
2319 return value > weakEps() || value < -weakEps();
2325 return value != (
signed char)(0);
2331 return value != (
unsigned char)(0);
2337 return value != short(0);
2343 return value != (
unsigned short)(0);
2367 return value != 0ul;
2373 return value != 0ll;
2379 return value != 0ull;
2382template <
typename T>
2385 return value.real() > weakEps() || value.real() < -weakEps() || value.imag() > weakEps() || value.imag() < -weakEps();
2388template <
typename T>
2391 return fabs(first - second) <= eps();
2397 return first == second;
2403 return first == second;
2409 return first == second;
2415 return first == second;
2421 return first == second;
2427 return first == second;
2433 return first == second;
2439 return first == second;
2445 return first == second;
2451 return first == second;
2454template <
typename T>
2457 return isEqual(first.real(), second.real()) && isEqual(first.imag(), second.imag());
2460template <
typename T>
2463 ocean_assert(epsilon >= T(0));
2470 ocean_assert(epsilon >= (
signed char)(0));
2471 return std::abs(first - second) <= epsilon;
2477 ocean_assert(epsilon >=
short(0));
2478 return std::abs(first - second) <= epsilon;
2484 ocean_assert(epsilon >= 0);
2485 return std::abs(first - second) <= epsilon;
2491 ocean_assert(epsilon >=
long(0));
2492 return std::abs(first - second) <= epsilon;
2498 ocean_assert(epsilon >= 0ll);
2499 return std::abs(first - second) <= epsilon;
2507 return first - second <= epsilon;
2511 return second - first <= epsilon;
2520 return first - second <= epsilon;
2524 return second - first <= epsilon;
2533 return first - second <= epsilon;
2537 return second - first <= epsilon;
2546 return first - second <= epsilon;
2550 return second - first <= epsilon;
2559 return first - second <= epsilon;
2563 return second - first <= epsilon;
2567template <
typename T>
2570 ocean_assert(epsilon >= T(0));
2571 return isEqual(first.real(), second.real(), epsilon) && isEqual(first.imag(), second.imag(), epsilon);
2574template <
typename T>
2583 return first == second;
2586template <
typename T>
2589 return isWeakEqual(first.real(), second.real()) && isWeakEqual(first.imag(), second.imag());
2592template <
typename T>
2593template <
int tMagnitude>
2596 static_assert(tMagnitude >= -20 && tMagnitude <= 20,
"Invalid reference magnitude");
2597 ocean_assert(referenceEpsilon >= T(0));
2602 if (isEqualEps(maximalAbsValue))
2608 ocean_assert(offsetMagnitude >= 0);
2610 const T adjustedEpsilon = referenceEpsilon *
NumericT<T>::pow(10, T(offsetMagnitude));
2612 return isEqual(first, second, adjustedEpsilon);
2615template <
typename T>
2618 return fabs(first - second) > eps();
2624 return first != second;
2630 return first != second;
2636 return first != second;
2642 return first != second;
2648 return first != second;
2654 return first != second;
2660 return first != second;
2666 return first != second;
2673 return first != second;
2679 return first != second;
2682template <
typename T>
2685 return isNotEqual(first.real(), second.real()) || isNotEqual(first.imag(), second.imag());
2688template <
typename T>
2691 return fabs(first - second) > weakEps();
2697 return first != second;
2703 return first != second;
2709 return first != second;
2715 return first != second;
2721 return first != second;
2727 return first != second;
2733 return first != second;
2739 return first != second;
2745 return first != second;
2751 return first != second;
2754template <
typename T>
2757 return isNotWeakEqual(first.real(), second.real()) || isNotWeakEqual(first.imag(), second.imag());
2760template <
typename T>
2763 ocean_assert(epsilon >= 0);
2764 return fabs(first - second) > epsilon;
2770 ocean_assert(epsilon >= (
signed char)(0));
2771 return std::abs(first - second) > epsilon;
2777 ocean_assert(epsilon >=
short(0));
2778 return std::abs(first - second) > epsilon;
2784 ocean_assert(epsilon >= 0);
2785 return std::abs(first - second) > epsilon;
2791 ocean_assert(epsilon >=
long(0));
2792 return std::abs(first - second) > epsilon;
2798 ocean_assert(epsilon >= 0ll);
2799 return std::abs(first - second) > epsilon;
2807 return first - second > epsilon;
2811 return second - first > epsilon;
2820 return first - second > epsilon;
2824 return second - first > epsilon;
2833 return first - second > epsilon;
2837 return second - first > epsilon;
2846 return first - second > epsilon;
2850 return second - first > epsilon;
2859 return first - second > epsilon;
2863 return second - first > epsilon;
2867template <
typename T>
2870 ocean_assert(epsilon >= 0);
2871 return isNotEqual(first.real(), second.real(), epsilon) || isNotEqual(first.imag(), second.imag(), epsilon);
2874template <
typename T>
2877 ocean_assert(lower <= upper);
2878 ocean_assert(epsilon >= T(0));
2880 return value >= lower - epsilon && value <= upper + epsilon;
2883template <
typename T>
2886 return isInsideRange(lower, value, upper, weakEps());
2889template <
typename T>
2894 return ::asin(max(T(-1), min(T(1), value)));
2906 return asinf(max(-1.0f, min(1.0f, value)));
2909template <
typename T>
2914 return ::acos(max(T(-1), min(T(1), value)));
2926 return acosf(max(-1.0f, min(1.0f, value)));
2929template <
typename T>
2932 static_assert(std::is_floating_point<T>::value,
"Invalid data type!");
2934 ocean_assert(epsilon >= T(0));
2936 return value <= upper + epsilon;
2939template <
typename T>
2942 static_assert(std::is_floating_point<T>::value,
"Invalid data type!");
2944 ocean_assert(epsilon >= T(0));
2946 return lower - epsilon <= value;
2949template <
typename T>
2952 static_assert(std::is_floating_point<T>::value,
"Data type must be a floating point data type");
2954 if constexpr (std::is_same<T, float>::value)
2956 static_assert(
sizeof(float) ==
sizeof(uint32_t),
"Invalid data type!");
2958 constexpr uint32_t integerValue = 0x7FC00000u;
2960 float floatValue = 0.0f;
2961 memcpy(&floatValue, &integerValue,
sizeof(integerValue));
2963 return T(floatValue);
2967 static_assert(std::is_same<T, double>::value,
"Invalid data type!");
2968 static_assert(
sizeof(double) ==
sizeof(uint64_t),
"Invalid data type!");
2970 constexpr uint64_t integerValue = 0x7FF8000000000000ull;
2972 double doubleValue = 0.0;
2973 memcpy(&doubleValue, &integerValue,
sizeof(integerValue));
2975 return T(doubleValue);
2985 static_assert(
sizeof(uint32_t) ==
sizeof(value),
"Invalid value!");
2990 memcpy(&tmpValue, &value,
sizeof(tmpValue));
2992 constexpr uint32_t exponentBitsAllOne = 0x7F800000u;
2993 constexpr uint32_t mantissaBitsAllOne = 0x007FFFFFu;
2995 const bool allExponentBitsAreOne = (tmpValue & exponentBitsAllOne) == exponentBitsAllOne;
2996 const bool mantissaIsNotZero = (tmpValue & mantissaBitsAllOne) != 0u;
2998 return allExponentBitsAreOne && mantissaIsNotZero;
3007 static_assert(
sizeof(uint64_t) ==
sizeof(value),
"Invalid value!");
3012 memcpy(&tmpValue, &value,
sizeof(tmpValue));
3014 constexpr uint64_t exponentBitsAllOne = 0x7FF0000000000000ull;
3015 constexpr uint64_t mantissaBitsAllOne = 0x000FFFFFFFFFFFFFull;
3017 const bool allExponentBitsAreOne = (tmpValue & exponentBitsAllOne) == exponentBitsAllOne;
3018 const bool mantissaIsNotZero = (tmpValue & mantissaBitsAllOne) != 0ull;
3020 return allExponentBitsAreOne && mantissaIsNotZero;
3023template <
typename T>
3029 ocean_assert(std::is_floating_point<T>::value ==
false);
3033template <
typename T>
3039template <
typename T>
3042 static_assert(std::is_floating_point<T>::value,
"Data type must be a floating point data type");
3044 if constexpr (std::is_same<T, float>::value)
3046 static_assert(
sizeof(float) ==
sizeof(uint32_t),
"Invalid data type!");
3048 constexpr uint32_t integerValue = 0x7F800000u;
3050 float floatValue = 0.0f;
3051 memcpy(&floatValue, &integerValue,
sizeof(integerValue));
3053 return T(floatValue);
3057 static_assert(std::is_same<T, double>::value,
"Invalid data type!");
3058 static_assert(
sizeof(double) ==
sizeof(uint64_t),
"Invalid data type!");
3060 constexpr uint64_t integerValue = 0x7FF0000000000000ull;
3062 double doubleValue = 0.0;
3063 memcpy(&doubleValue, &integerValue,
sizeof(integerValue));
3065 return T(doubleValue);
3075 static_assert(
sizeof(uint32_t) ==
sizeof(value),
"Invalid value!");
3080 memcpy(&tmpValue, &value,
sizeof(tmpValue));
3082 constexpr uint32_t exponentBitsAllOne = 0x7F800000u;
3083 constexpr uint32_t mantissaBitsAllOne = 0x007FFFFFu;
3085 const bool allExponentBitsAreOne = (tmpValue & exponentBitsAllOne) == exponentBitsAllOne;
3086 const bool allMantissaBitsAreZero = (tmpValue & mantissaBitsAllOne) == 0u;
3088 return allExponentBitsAreOne && allMantissaBitsAreZero;
3097 static_assert(
sizeof(uint64_t) ==
sizeof(value),
"Invalid value!");
3102 memcpy(&tmpValue, &value,
sizeof(tmpValue));
3104 constexpr uint64_t exponentBitsAllOne = 0x7FF0000000000000ull;
3105 constexpr uint64_t mantissaBitsAllOne = 0x000FFFFFFFFFFFFFull;
3107 const bool allExponentBitsAreOne = (tmpValue & exponentBitsAllOne) == exponentBitsAllOne;
3108 const bool allMantissaBitsAreZero = (tmpValue & mantissaBitsAllOne) == 0ull;
3110 return allExponentBitsAreOne && allMantissaBitsAreZero;
3113template <
typename T>
3119 ocean_assert(std::is_floating_point<T>::value ==
false);
3126 return std::isinf(value);
3129template <
typename T>
3135template <
typename T>
3136template <
typename TValue>
3139 if constexpr (std::is_same<T, TValue>::value)
3146 if constexpr (std::is_floating_point<T>::value && std::is_floating_point<TValue>::value)
3155 if constexpr (std::is_integral<T>::value && std::is_integral<TValue>::value)
3159 if constexpr (std::is_signed<T>::value == std::is_signed<TValue>::value)
3163 if constexpr (
sizeof(TValue) <=
sizeof(T))
3171 ocean_assert(
sizeof(T) <
sizeof(TValue));
3179 if constexpr (std::is_signed<T>::value)
3181 ocean_assert(!std::is_signed<TValue>::value);
3185 if constexpr (
sizeof(TValue) <
sizeof(T))
3197 if constexpr (std::is_signed<TValue>::value)
3199 ocean_assert(!std::is_signed<T>::value);
3203 if (value < TValue(0))
3208 if constexpr (
sizeof(TValue) <
sizeof(T))
3214 else if constexpr (
sizeof(TValue) ==
sizeof(T))
3218 ocean_assert(value >= TValue(0));
3225 ocean_assert(value >= TValue(0));
3234template <
typename T>
3237 return deg * T(0.017453292519943295769236907684886);
3240template <
typename T>
3243 return rad * T(57.295779513082320876798154814105);
3246template <
typename T>
3249 return std::numeric_limits<T>::max();
3252template <
typename T>
3255 return std::numeric_limits<T>::lowest();
3258template <
typename T>
3261 static_assert(std::numeric_limits<T>::is_signed,
"T must be a signed data type!");
3263 return T((T(0) < value) - (value < T(0)));
3266template <
typename T>
3269 if (signProvider >= 0)
3271 return abs(signReceiver);
3274 return -abs(signReceiver);
3286 const uint64_t value = ((*(uint64_t*)&first) & 0x7FFFFFFFFFFFFFFFull)
3287 | ((*(uint64_t*)&second) & 0x8000000000000000ull);
3291 ocean_assert(
sizeof(uint64_t) ==
sizeof(
double));
3293 const double result = *(
double*)(&value);
3295 double testValue = 0;
3306 ocean_assert(result == testValue || second == 0.0);
3310 return *(
double*)&value;
3320 const uint32_t value = ((*(uint32_t*)&first) & 0x7FFFFFFFu) | ((*(uint32_t*)&second) & 0x80000000u);
3324 ocean_assert(
sizeof(uint32_t) ==
sizeof(
float));
3326 const float result = *(
float*)(&value);
3328 float testValue = 0;
3339 ocean_assert(result == testValue || second == 0.0);
3343 return *(
float*)&value;
3348template <
typename T>
3351 if (signProvider < 0)
3353 return abs(signReceiver);
3356 return -abs(signReceiver);
3368 const uint64_t value = ((*(uint64_t*)&first) & 0x7FFFFFFFFFFFFFFFull)
3369 | ((~*(uint64_t*)&second) & 0x8000000000000000ull);
3373 ocean_assert(
sizeof(uint64_t) ==
sizeof(
double));
3375 const double result = *(
double*)&value;
3377 double testValue = 0;
3388 ocean_assert(result == testValue);
3393 return *(
double*)&value;
3403 const uint32_t value = ((*(uint32_t*)&first) & 0x7FFFFFFFu) | ((~*(uint32_t*)&second) & 0x80000000u);
3407 ocean_assert(
sizeof(uint32_t) ==
sizeof(
float));
3409 const float result = *(
float*)&value;
3411 double testValue = 0;
3422 ocean_assert(result == testValue);
3426 return *(
float*)&value;
3431template <
typename T>
3439 const T factor = absB / absA;
3440 return absA * sqrt(1 + factor * factor);
3444 const T factor = absA / absB;
3445 return absB * sqrt(1 + factor * factor);
3451template <
typename T>
3454 ocean_assert(sigma > eps());
3456 const T inverseSigma = T(1) / sigma;
3458 return inverseSigma * T(0.3989422804014326779) *
NumericT<T>::exp(T(-0.5) * x * x * inverseSigma * inverseSigma);
3461template <
typename T>
3464 ocean_assert(sigma > eps());
3466 const T inverseSigma = T(1) / sigma;
3467 const T x_x0 = x - x0;
3469 return inverseSigma * T(0.3989422804014326779) *
NumericT<T>::exp(T(-0.5) * x_x0 * x_x0 * inverseSigma * inverseSigma);
3472template <
typename T>
3475 ocean_assert(sigma > eps());
3477 const T inverseSigma = T(1) / sigma;
3482template <
typename T>
3485 ocean_assert(sigma > eps());
3487 const T inverseSigma = T(1) / sigma;
3488 const T x_x0 = x - x0;
3490 return NumericT<T>::exp(T(-0.5) * x_x0 * x_x0 * inverseSigma * inverseSigma);
3493template <
typename T>
3496 ocean_assert(sigmaX > eps() && sigmaY > eps());
3498 const T inverseSigmaX = T(1) / sigmaX;
3499 const T inverseSigmaY = T(1) / sigmaY;
3501 return inverseSigmaX * inverseSigmaY * T(0.15915494309189533576888) *
NumericT<T>::exp(T(-0.5) * (x * x * inverseSigmaX * inverseSigmaX + y * y * inverseSigmaY * inverseSigmaY));
3504template <
typename T>
3507 ocean_assert(sigmaX > eps() && sigmaY > eps());
3509 const T inverseSigmaX = T(1) / sigmaX;
3510 const T inverseSigmaY = T(1) / sigmaY;
3512 const T x_x0 = x - x0;
3513 const T y_y0 = y - y0;
3515 return inverseSigmaX * inverseSigmaY * T(0.15915494309189533576888) *
NumericT<T>::exp(T(-0.5) * (x_x0 * x_x0 * inverseSigmaX * inverseSigmaX + y_y0 * y_y0 * inverseSigmaY * inverseSigmaY));
3518template <
typename T>
3521 ocean_assert(sigmaX > eps() && sigmaY > eps());
3523 const T inverseSigmaX = T(1) / sigmaX;
3524 const T inverseSigmaY = T(1) / sigmaY;
3526 return NumericT<T>::exp(T(-0.5) * (x * x * inverseSigmaX * inverseSigmaX + y * y * inverseSigmaY * inverseSigmaY));
3529template <
typename T>
3532 ocean_assert(sigmaX > eps() && sigmaY > eps());
3534 const T inverseSigmaX = T(1) / sigmaX;
3535 const T inverseSigmaY = T(1) / sigmaY;
3537 const T x_x0 = x - x0;
3538 const T y_y0 = y - y0;
3540 return NumericT<T>::exp(T(-0.5) * (x_x0 * x_x0 * inverseSigmaX * inverseSigmaX + y_y0 * y_y0 * inverseSigmaY * inverseSigmaY));
3543template <
typename T>
3546 ocean_assert(sigmaX > eps() && sigmaY > eps() && sigmaZ > eps());
3548 const T inverseSigmaX = T(1) / sigmaX;
3549 const T inverseSigmaY = T(1) / sigmaY;
3550 const T inverseSigmaZ = T(1) / sigmaZ;
3552 return inverseSigmaX * inverseSigmaY * inverseSigmaZ * T(0.06349363593424096978576330493464)
3553 *
NumericT<T>::exp(T(-0.5) * (x * x * inverseSigmaX * inverseSigmaX + y * y * inverseSigmaY * inverseSigmaY + z * z * inverseSigmaZ * inverseSigmaZ));
3556template <
typename T>
3559 ocean_assert(sigmaX > eps() && sigmaY > eps() && sigmaZ > eps());
3561 const T inverseSigmaX = T(1) / sigmaX;
3562 const T inverseSigmaY = T(1) / sigmaY;
3563 const T inverseSigmaZ = T(1) / sigmaZ;
3565 const T x_x0 = x - x0;
3566 const T y_y0 = y - y0;
3567 const T z_z0 = z - z0;
3569 return inverseSigmaX * inverseSigmaY * inverseSigmaZ * T(0.06349363593424096978576330493464)
3570 *
NumericT<T>::exp(T(-0.5) * (x_x0 * x_x0 * inverseSigmaX * inverseSigmaX + y_y0 * y_y0 * inverseSigmaY * inverseSigmaY + z_z0 * z_z0 * inverseSigmaZ * inverseSigmaZ));
3573template <
typename T>
3576 ocean_assert(sigmaX > eps() && sigmaY > eps() && sigmaZ > eps());
3578 const T inverseSigmaX = T(1) / sigmaX;
3579 const T inverseSigmaY = T(1) / sigmaY;
3580 const T inverseSigmaZ = T(1) / sigmaZ;
3582 return NumericT<T>::exp(T(-0.5) * (x * x * inverseSigmaX * inverseSigmaX + y * y * inverseSigmaY * inverseSigmaY + z * z * inverseSigmaZ * inverseSigmaZ));
3585template <
typename T>
3588 ocean_assert(sigmaX > eps() && sigmaY > eps() && sigmaZ > eps());
3590 const T inverseSigmaX = T(1) / sigmaX;
3591 const T inverseSigmaY = T(1) / sigmaY;
3592 const T inverseSigmaZ = T(1) / sigmaZ;
3594 const T x_x0 = x - x0;
3595 const T y_y0 = y - y0;
3596 const T z_z0 = z - z0;
3598 return NumericT<T>::exp(T(-0.5) * (x_x0 * x_x0 * inverseSigmaX * inverseSigmaX + y_y0 * y_y0 * inverseSigmaY * inverseSigmaY + z_z0 * z_z0 * inverseSigmaZ * inverseSigmaZ));
This class provides basic numeric functionalities.
Definition Numeric.h:57
static T angleAdjustPositive(const T angle)
Adjusts an arbitrary angle into the range of [0.0, 2PI).
Definition Numeric.h:1764
static constexpr T deg2rad(const T deg)
Converts deg to rad.
Definition Numeric.h:3235
static constexpr bool isNotWeakEqualEps(const T value)
Returns whether a value is not smaller than or equal to a weak epsilon.
Definition Numeric.h:2315
static constexpr T minValue()
Returns the min scalar value.
Definition Numeric.h:3253
static constexpr T pi2()
Returns 2*PI which is equivalent to 360 degree.
Definition Numeric.h:932
static constexpr T sign(const T &value)
Returns the sign of a given value by either returning -1, 0, or +1.
Definition Numeric.h:3259
static constexpr T weakEps()
Returns a weak epsilon.
static constexpr bool isInsideRange(const T lower, const T value, const T upper, const T epsilon=NumericT< T >::eps())
Returns whether a value lies between a given range up to a provided epsilon border.
Definition Numeric.h:2875
static constexpr T pi_2()
Returns PI/2 which is equivalent to 90 degree.
Definition Numeric.h:938
static T log(const T value)
Returns the natural logarithm of a given value (the logarithm to the base e).
Definition Numeric.h:1655
static T exp(const T value)
Returns the base-e exponential function of a given value.
Definition Numeric.h:1643
static T log1p(const T value)
Returns the natural logarithm of a given value plus 1 (the logarithm to the base e).
Definition Numeric.h:1669
static constexpr T e()
Returns the euler's number.
Definition Numeric.h:974
static T atan(const T value)
Returns the arctangent of a given value.
Definition Numeric.h:1616
static T atan2(const T y, const T x)
Returns the arctangent of a given value in radian.
Definition Numeric.h:1632
static constexpr T sqrDistance(const T value0, const T value1)
Returns the square distance between two values.
Definition Numeric.h:1527
static T sin(const T value)
Returns the sine of a given value.
Definition Numeric.h:1568
static bool isInf(const T value)
Returns whether a given value is positive or negative infinity.
Definition Numeric.h:3114
static T pow(const T x, const T y)
Returns x raised to the power of y.
Definition Numeric.h:1860
static constexpr T pi_4()
Returns PI/4 which is equivalent to 45 degree.
Definition Numeric.h:950
static bool isNan(const T value)
Returns whether a given value is not a number.
Definition Numeric.h:3024
static T abs(const T value)
Returns the absolute value of a given value.
Definition Numeric.h:1220
static constexpr T factorial(const T &value)
Returns the factorial for a given value.
Definition Numeric.h:1888
static constexpr T pi()
Returns PI which is equivalent to 180 degree.
Definition Numeric.h:926
static T log10(const T value)
Returns the logarithm to base 10 of a given value.
Definition Numeric.h:1711
static constexpr T squarePi2()
Returns the square of two PI i.e., (2*PI)^2.
Definition Numeric.h:962
static constexpr bool isAbove(const T value, const T lower, const T epsilon=NumericT< T >::eps())
Returns whether a parameter lies on or above a given border tolerating a small epsilon.
Definition Numeric.h:2940
static bool isWeakEqual(const T first, const T second)
Returns whether two values a equal up to a weak epsilon.
Definition Numeric.h:2575
static T normalizedGaussianDistribution(const T x, const T sigma)
Returns a value of the normalized univariate Gaussian distribution centered around the origin.
Definition Numeric.h:3473
static constexpr int32_t round32(const T value)
Returns the rounded 32 bit integer value of a given value.
Definition Numeric.h:2067
static T sum(const T *values, const size_t number)
Returns the sum of given values.
Definition Numeric.h:1501
static constexpr bool isWeakEqualEps(const T value)
Returns whether a value is smaller than or equal to a weak epsilon.
Definition Numeric.h:2165
static T sqrt(const T value)
Returns the square root of a given value.
Definition Numeric.h:1533
static T pythagoras(const T a, const T b)
Returns the length of the hypotenuse of a given right-angled triangle.
Definition Numeric.h:3432
static T fmod(const T valueA, const T valueB)
Returns the floating-point remainder of a given value.
Definition Numeric.h:1735
static T angleAdjustNull(const T angle)
Adjusts an arbitrary angle into the range of (-PI, PI].
Definition Numeric.h:1794
static bool angleIsBelowThreshold(const T angleA, const T angleB, const T threshold)
Returns whether the angular difference (distance) between two angles is smaller than a specified thre...
Definition Numeric.h:1838
static constexpr T eps()
Returns a small epsilon.
static bool isEqual(const T first, const T second)
Returns whether two values are equal up to a small epsilon.
Definition Numeric.h:2389
static constexpr bool isBelow(const T value, const T upper, const T epsilon=NumericT< T >::eps())
Returns whether a parameter lies on or below a given border tolerating a small epsilon.
Definition Numeric.h:2930
static T gaussianDistribution(const T x, const T sigma)
Returns a value of the univariate Gaussian distribution centered around the origin.
Definition Numeric.h:3452
static T gaussianDistribution2(const T x, const T y, const T sigmaX, const T sigmaY)
Returns a value of the bivariate Gaussian distribution centered around the origin.
Definition Numeric.h:3494
static constexpr T ratio(const T nominator, const T denominator, const T fallback=T(1))
Returns the ratio between two values if the denominator is not equal a small epsilon.
Definition Numeric.h:2079
static constexpr T nan()
Returns a value which is not a number (nan).
Definition Numeric.h:2950
static constexpr T squarePi_2()
Returns the square of PI half i.e., (PI/2)^2.
Definition Numeric.h:968
static T floor(const T value)
Returns the largest integer value that is not greater than the given value.
Definition Numeric.h:2029
static constexpr T integerPow(const T x, const unsigned int y)
Returns x raised to the power of y while y is an integer.
Definition Numeric.h:1882
static constexpr T squarePi()
Returns the square of PI i.e., PI^2.
Definition Numeric.h:956
static T tan(const T value)
Returns the tangent of a given value.
Definition Numeric.h:1600
static T normalizedGaussianDistribution3(const T x, const T y, const T z, const T sigmaX, const T sigmaY, const T sigmaZ)
Returns a value of the normalized trivariate Gaussian distribution centered around the origin.
Definition Numeric.h:3574
static UnsignedTyper< T >::Type secureAbs(const T value)
Returns the absolute value of a given value while the return value is guaranteed to be the absolute v...
Definition Numeric.h:1356
static T ceil(const T value)
Returns the smallest integer value that is not less than the given value.
Definition Numeric.h:1991
static constexpr int64_t round64(const T value)
Returns the rounded 64 bit integer value of a given value.
Definition Numeric.h:2073
static bool angleIsEqual(const T angleA, const T angleB)
Returns whether two angles represent the same angle up to a small epsilon.
Definition Numeric.h:1819
static constexpr T pi_3()
Returns PI/3 which is equivalent to 60 degree.
Definition Numeric.h:944
static constexpr T sqr(const T value)
Returns the square of a given value.
Definition Numeric.h:1495
static T angleAdjustPositiveHalf(const T angle)
Adjusts an arbitrary angle into the range of [0.0, PI).
Definition Numeric.h:1779
static constexpr bool isInsideWeakRange(const T lower, const T value, const T upper)
Returns whether a value lies between a given range up to a weak epsilon border.
Definition Numeric.h:2884
static T normalizedGaussianDistribution2(const T x, const T y, const T sigmaX, const T sigmaY)
Returns a value of the normalized bivariate Gaussian distribution centered around the origin.
Definition Numeric.h:3519
static constexpr bool isEqualEps(const T value)
Returns whether a value is smaller than or equal to a small epsilon.
Definition Numeric.h:2090
static constexpr T copySign(const T signReceiver, const T signProvider)
Copies the sign of a given value to another one.
Definition Numeric.h:3267
static constexpr T rad2deg(const T rad)
Converts rad to deg.
Definition Numeric.h:3241
static T cos(const T value)
Returns the cosine of a given value.
Definition Numeric.h:1584
static T gaussianDistribution3(const T x, const T y, const T z, const T sigmaX, const T sigmaY, const T sigmaZ)
Returns a value of the trivariate Gaussian distribution centered around the origin.
Definition Numeric.h:3544
static T dot(const T *vectorA, const T *vectorB, const size_t size)
Returns the dot product for two vectors.
Definition Numeric.h:1751
static bool isInsideValueRange(const TValue &value)
Returns whether a given value of an arbitrary data type fits into the value range of 'T'.
Definition Numeric.h:3137
static T acos(const T value)
Returns the arccosine of a given value.
Definition Numeric.h:2910
static constexpr T invertSign(const T signReceiver, const T signProvider)
Copies the inverted sign of a given value to another one.
Definition Numeric.h:3349
static constexpr T inf()
Returns a value which is positive infinity.
Definition Numeric.h:3040
static constexpr bool isNotEqualEps(const T value)
Returns whether a value is not smaller than or equal to a small epsilon.
Definition Numeric.h:2240
static bool angleIsWeakEqual(const T angleA, const T angleB)
Returns whether two angles represent the same angle up to a weak epsilon.
Definition Numeric.h:1825
static T angleDistance(const T angleA, const T angleB)
Returns the angular difference (distance between two angles).
Definition Numeric.h:1846
static bool isNotEqual(const T first, const T second)
Returns whether two values are not equal up to a small epsilon.
Definition Numeric.h:2616
static T summedSqr(const T *values, const size_t number)
Returns the summed squares of a given values.
Definition Numeric.h:1514
static T log2(const T value)
Returns the logarithm to base 2 of a given value.
Definition Numeric.h:1683
static constexpr T maxValue()
Returns the max scalar value.
Definition Numeric.h:3247
static T asin(const T value)
Returns the arcsine of a given value.
Definition Numeric.h:2890
static bool isNotWeakEqual(const T first, const T second)
Returns whether two values are not equal up to a weak epsilon.
Definition Numeric.h:2689
static constexpr T binomialCoefficient(const T &n, const T &k)
Returns the binomial coefficient for two binomial parameters.
Definition Numeric.h:1960
T Type
Definition of the unsigned data type, if existing.
Definition DataType.h:339
unsigned int sqr(const char value)
Returns the square value of a given value.
Definition base/Utilities.h:1053
NumericT< Scalar > Numeric
Definition of a Numeric class.
Definition Numeric.h:33
NumericT< float > NumericF
Definition of a Numeric class with float values.
Definition Numeric.h:47
NumericT< double > NumericD
Definition of a Numeric class with double values.
Definition Numeric.h:40
The namespace covering the entire Ocean framework.
Definition Accessor.h:15