bool_algebra.hpp 3.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130
  1. #ifndef SIMPLE_GEOM_BOOL_ALGEBRA_HPP
  2. #define SIMPLE_GEOM_BOOL_ALGEBRA_HPP
  3. #include "reduction.hpp"
  4. #include "vector.hpp"
  5. namespace simple::geom
  6. {
  7. struct conjunct
  8. {
  9. static constexpr bool identity = true;
  10. // NOTE: passing by value here prevented short circuiting
  11. // gcc 9.3.0
  12. // gcc 7.5.0
  13. constexpr bool operator()(const bool& a, const bool& b) const noexcept
  14. {
  15. return a && b;
  16. }
  17. };
  18. struct disjunct
  19. {
  20. static constexpr bool identity = false;
  21. // NOTE: passing by value here prevented short circuiting
  22. // gcc 9.3.0
  23. // gcc 7.5.0
  24. constexpr bool operator()(const bool& a, const bool& b) const noexcept
  25. {
  26. return a || b;
  27. }
  28. };
  29. // TODO: guess need to support compatibility_tag from support/array_operators.hpp :/
  30. #define SIMPLE_GEOM_VECTOR_DEFINE_COMPARISON_OPERATOR(op, reduce_method) \
  31. template <typename C1, typename C2, size_t D, typename O, \
  32. typename Bool = \
  33. typename vector<C1, D, O>::template map_coordinate_t<bool> \
  34. > \
  35. [[nodiscard]] \
  36. constexpr reduction<reduce_method, Bool, bool> \
  37. operator op(const vector<C1,D,O>& one, const vector<C2,D,O>& other) \
  38. { \
  39. Bool ret{}; \
  40. for(size_t i = 0; i < D; ++i) \
  41. ret[i] = (one[i] op other[i]); \
  42. return reduction<reduce_method, Bool, bool>(ret); \
  43. }
  44. SIMPLE_GEOM_VECTOR_DEFINE_COMPARISON_OPERATOR(==, conjunct)
  45. SIMPLE_GEOM_VECTOR_DEFINE_COMPARISON_OPERATOR(!=, disjunct)
  46. SIMPLE_GEOM_VECTOR_DEFINE_COMPARISON_OPERATOR(>, conjunct)
  47. SIMPLE_GEOM_VECTOR_DEFINE_COMPARISON_OPERATOR(>=, conjunct)
  48. SIMPLE_GEOM_VECTOR_DEFINE_COMPARISON_OPERATOR(<, conjunct)
  49. SIMPLE_GEOM_VECTOR_DEFINE_COMPARISON_OPERATOR(<=, conjunct)
  50. #undef SIMPLE_GEOM_VECTOR_DEFINE_COMPARISON_OPERATOR
  51. template <typename C, size_t D, typename O>
  52. using conjunction = reduction<
  53. conjunct, vector<C,D,O> >;
  54. template <typename C, size_t D, typename O>
  55. using disjunction = reduction<
  56. disjunct, vector<C,D,O> >;
  57. template <typename C, size_t D, typename O>
  58. [[nodiscard]] constexpr
  59. conjunction<C,D,O> to_conjunction(vector<C,D,O> v)
  60. {
  61. return conjunction<C,D,O>(v);
  62. }
  63. template <typename C, size_t D, typename O>
  64. [[nodiscard]] constexpr
  65. conjunction<C,D,O> to_conjunction(disjunction<C,D,O> v)
  66. {
  67. return conjunction<C,D,O>(v.range);
  68. }
  69. template <typename C, size_t D, typename O>
  70. [[nodiscard]] constexpr
  71. disjunction<C,D,O> to_disjunction(vector<C,D,O> v)
  72. {
  73. return disjunction<C,D,O>(v);
  74. }
  75. template <typename C, size_t D, typename O>
  76. [[nodiscard]] constexpr
  77. disjunction<C,D,O> to_disjunction(conjunction<C,D,O> v)
  78. {
  79. return disjunction<C,D,O>(v.range);
  80. }
  81. // De Morgan's laws
  82. template <typename C, size_t D, typename O>
  83. [[nodiscard]] constexpr conjunction<C,D,O>
  84. operator~(const disjunction<C,D,O>& one) noexcept
  85. {
  86. return conjunction<C,D,O>(~(one.range));
  87. }
  88. template <typename C, size_t D, typename O>
  89. [[nodiscard]] constexpr disjunction<C,D,O>
  90. operator~(const conjunction<C,D,O>& one) noexcept
  91. {
  92. return disjunction<C,D,O>(~(one.range));
  93. }
  94. } // namespace simple::geom
  95. namespace simple
  96. {
  97. template <typename C, size_t D, typename O>
  98. struct support::array_operator_implicit_conversion<
  99. geom::disjunction<C,D,O>>
  100. {
  101. using type = typename geom::disjunction<C,D,O>::
  102. range_type::template map_coordinate_t<bool>;
  103. };
  104. template <typename C, size_t D, typename O>
  105. struct support::array_operator_implicit_conversion<
  106. geom::conjunction<C,D,O>>
  107. {
  108. using type = typename geom::conjunction<C,D,O>::
  109. range_type::template map_coordinate_t<bool>;
  110. };
  111. } // namespace simple
  112. #endif /* end of include guard */