BioCMAMC-ST
traits.hpp
1#ifndef __COMMON_TRAITS_HPP__
2#define __COMMON_TRAITS_HPP__
3#include <cmath>
4#include <type_traits>
5
6#if defined __GNUC__
7# define LIKELY(EXPR) __builtin_expect(!!(EXPR), 1)
8#else
9# define LIKELY(EXPR) (!!(EXPR))
10#endif
11
12#if defined NDEBUG
13# define X_ASSERT(CHECK) void(0)
14#else
15# define X_ASSERT(CHECK) \
16 ( LIKELY(CHECK) ? void(0) : []{assert(!#CHECK);}() )
17#endif
18
19template <typename T>
20concept FloatingPointType = std::is_floating_point_v<std::remove_cvref_t<T>>;
21
22constexpr double tolerance_equality_float = 1e-15;
23
24template <typename T>
25concept IntegerType = requires(T n) {
26 requires std::is_integral_v<std::remove_cvref_t<T>>;
27 requires !std::is_same_v<std::remove_cvref_t<T>, bool>;
28 requires std::is_arithmetic_v<decltype(n + 1)>;
29 requires !std::is_pointer_v<std::remove_cvref_t<T>>;
30};
31
32template <typename T>
34
35// General case: by value
36template <NumberType T>
37inline bool almost_equal(T val, T val2, T tolerance = tolerance_equality_float)
38{
39 using CommonT = std::common_type_t<T, T>;
40 return std::abs(static_cast<CommonT>(val) - static_cast<CommonT>(val2)) <
41 static_cast<CommonT>(tolerance);
42}
43
44// Overload for references
45template <NumberType T>
46inline bool almost_equal(const T& val, const T& val2, T tolerance = tolerance_equality_float)
47{
48 using CommonT = std::common_type_t<T, T>;
49 return std::abs(static_cast<CommonT>(val) - static_cast<CommonT>(val2)) <
50 static_cast<CommonT>(tolerance);
51}
52
53// Overload for pointers
54template <NumberType T>
55inline bool almost_equal(const T* val, const T* val2, T tolerance = tolerance_equality_float)
56{
57 if (!val || !val2)
58 {
59 return false; // Null pointer check
60 }
61 using CommonT = std::common_type_t<T, T>;
62 return std::abs(static_cast<CommonT>(*val) - static_cast<CommonT>(*val2)) <
63 static_cast<CommonT>(tolerance);
64}
65
66// Overload for rvalue references
67template <NumberType T>
68inline bool almost_equal(T&& val, T&& val2, T tolerance = tolerance_equality_float)
69{
70 using CommonT = std::common_type_t<T, T>;
71 return std::abs(static_cast<CommonT>(val) - static_cast<CommonT>(val2)) <
72 static_cast<CommonT>(tolerance);
73}
74
75#endif
Definition traits.hpp:20
Definition traits.hpp:25
Definition traits.hpp:33