Преглед на файлове

memory: turn the power-of-two/fast_mod toolset into a non-constexpr one

Michele Caini преди 3 години
родител
ревизия
57ad7696be
променени са 2 файла, в които са добавени 39 реда и са изтрити 48 реда
  1. 36 36
      src/entt/core/memory.hpp
  2. 3 12
      test/entt/core/memory.cpp

+ 36 - 36
src/entt/core/memory.hpp

@@ -11,6 +11,42 @@
 
 namespace entt {
 
+/**
+ * @brief Checks whether a value is a power of two or not.
+ * @param value A value that may or may not be a power of two.
+ * @return True if the value is a power of two, false otherwise.
+ */
+[[nodiscard]] inline bool is_power_of_two(const std::size_t value) noexcept {
+    return value && ((value & (value - 1)) == 0);
+}
+
+/**
+ * @brief Computes the smallest power of two greater than or equal to a value.
+ * @param value The value to use.
+ * @return The smallest power of two greater than or equal to the given value.
+ */
+[[nodiscard]] inline std::size_t next_power_of_two(const std::size_t value) noexcept {
+    ENTT_ASSERT(value < (std::size_t{1u} << (std::numeric_limits<std::size_t>::digits - 1)), "Numeric limits exceeded");
+    std::size_t curr = value - (value != 0u);
+
+    for(int next = 1; next < std::numeric_limits<std::size_t>::digits; next = next * 2) {
+        curr |= curr >> next;
+    }
+
+    return ++curr;
+}
+
+/**
+ * @brief Fast module utility function (powers of two only).
+ * @param value A value for which to calculate the modulus.
+ * @param mod _Modulus_, it must be a power of two.
+ * @return The common remainder.
+ */
+[[nodiscard]] inline std::size_t fast_mod(const std::size_t value, const std::size_t mod) noexcept {
+    ENTT_ASSERT(is_power_of_two(mod), "Value must be a power of two");
+    return value & (mod - 1u);
+}
+
 /**
  * @brief Unwraps fancy pointers, does nothing otherwise (waiting for C++20).
  * @tparam Type Pointer type.
@@ -68,42 +104,6 @@ constexpr void propagate_on_container_swap([[maybe_unused]] Allocator &lhs, [[ma
     }
 }
 
-/**
- * @brief Checks whether a value is a power of two or not.
- * @param value A value that may or may not be a power of two.
- * @return True if the value is a power of two, false otherwise.
- */
-[[nodiscard]] inline constexpr bool is_power_of_two(const std::size_t value) noexcept {
-    return value && ((value & (value - 1)) == 0);
-}
-
-/**
- * @brief Computes the smallest power of two greater than or equal to a value.
- * @param value The value to use.
- * @return The smallest power of two greater than or equal to the given value.
- */
-[[nodiscard]] inline constexpr std::size_t next_power_of_two(const std::size_t value) noexcept {
-    ENTT_ASSERT(value < (std::size_t{1u} << (std::numeric_limits<std::size_t>::digits - 1)), "Numeric limits exceeded");
-    std::size_t curr = value - (value != 0u);
-
-    for(int next = 1; next < std::numeric_limits<std::size_t>::digits; next = next * 2) {
-        curr |= curr >> next;
-    }
-
-    return ++curr;
-}
-
-/**
- * @brief Fast module utility function (powers of two only).
- * @param value A value for which to calculate the modulus.
- * @param mod _Modulus_, it must be a power of two.
- * @return The common remainder.
- */
-[[nodiscard]] inline constexpr std::size_t fast_mod(const std::size_t value, const std::size_t mod) noexcept {
-    ENTT_ASSERT(is_power_of_two(mod), "Value must be a power of two");
-    return value & (mod - 1u);
-}
-
 /**
  * @brief Deleter for allocator-aware unique pointers (waiting for C++20).
  * @tparam Args Types of arguments to use to construct the object.

+ 3 - 12
test/entt/core/memory.cpp

@@ -37,10 +37,7 @@ ENTT_DEBUG_TEST(PoccaPocmaAndPocsDeathTest, Functionalities) {
 }
 
 TEST(IsPowerOfTwo, Functionalities) {
-    // constexpr-ness guaranteed
-    constexpr auto zero_is_power_of_two = entt::is_power_of_two(0u);
-
-    ASSERT_FALSE(zero_is_power_of_two);
+    ASSERT_FALSE(entt::is_power_of_two(0u));
     ASSERT_TRUE(entt::is_power_of_two(1u));
     ASSERT_TRUE(entt::is_power_of_two(2u));
     ASSERT_TRUE(entt::is_power_of_two(4u));
@@ -50,10 +47,7 @@ TEST(IsPowerOfTwo, Functionalities) {
 }
 
 TEST(NextPowerOfTwo, Functionalities) {
-    // constexpr-ness guaranteed
-    constexpr auto next_power_of_two_of_zero = entt::next_power_of_two(0u);
-
-    ASSERT_EQ(next_power_of_two_of_zero, 1u);
+    ASSERT_EQ(entt::next_power_of_two(0u), 1u);
     ASSERT_EQ(entt::next_power_of_two(1u), 1u);
     ASSERT_EQ(entt::next_power_of_two(2u), 2u);
     ASSERT_EQ(entt::next_power_of_two(3u), 4u);
@@ -69,10 +63,7 @@ ENTT_DEBUG_TEST(NextPowerOfTwoDeathTest, Functionalities) {
 }
 
 TEST(FastMod, Functionalities) {
-    // constexpr-ness guaranteed
-    constexpr auto fast_mod_of_zero = entt::fast_mod(0u, 8u);
-
-    ASSERT_EQ(fast_mod_of_zero, 0u);
+    ASSERT_EQ(entt::fast_mod(0u, 8u), 0u);
     ASSERT_EQ(entt::fast_mod(7u, 8u), 7u);
     ASSERT_EQ(entt::fast_mod(8u, 8u), 0u);
 }