diff --git a/include/ircd/util/tuple.h b/include/ircd/util/tuple.h index ca9cdafaf..570da1ba7 100644 --- a/include/ircd/util/tuple.h +++ b/include/ircd/util/tuple.h @@ -44,45 +44,66 @@ size(const std::tuple &t) // // for_each(tuple, [](auto&& elem) { ... }); -template -constexpr typename std::enable_if>::value, void>::type -for_each(std::tuple &t, - func&& f) -{} - -template -constexpr -typename std::enable_if>::value, void>::type -for_each(const std::tuple &t, - func&& f) -{} - template -constexpr -typename std::enable_if>::value, void>::type +constexpr inline bool for_each(const std::tuple &t, func&& f) { - f(std::get(t)); - for_each(t, std::forward(f)); + if constexpr(i < size>()) + { + using closure_result = std::invoke_result_t + < + decltype(f), decltype(std::get(t)) + >; + + constexpr bool terminable + { + std::is_same() + }; + + if constexpr(terminable) + { + if(!f(std::get(t))) + return false; + } + else f(std::get(t)); + + return for_each(t, std::forward(f)); + } + else return true; } template -constexpr -typename std::enable_if>::value, void>::type +constexpr inline bool for_each(std::tuple &t, func&& f) { - f(std::get(t)); - for_each(t, std::forward(f)); + if constexpr(i < size>()) + { + using closure_result = std::invoke_result_t + < + decltype(f), decltype(std::get(t)) + >; + + constexpr bool terminable + { + std::is_same() + }; + + if constexpr(terminable) + { + if(!f(std::get(t))) + return false; + } + else f(std::get(t)); + + return for_each(t, std::forward(f)); + } + else return true; } // @@ -90,234 +111,92 @@ for_each(std::tuple &t, // // rfor_each(tuple, [](auto&& elem) { ... }); -template -constexpr -typename std::enable_if::type -rfor_each(const std::tuple &t, - func&& f) -{} - -template -constexpr -typename std::enable_if::type -rfor_each(std::tuple &t, - func&& f) -{} - -template -constexpr -typename std::enable_if<(i > 0), void>::type +template>() - 1> +constexpr inline bool rfor_each(const std::tuple &t, func&& f) { - f(std::get(t)); - rfor_each(t, std::forward(f)); + if constexpr(i >= 0) + { + using closure_result = std::invoke_result_t + < + decltype(f), decltype(std::get(t)) + >; + + constexpr bool terminable + { + std::is_same() + }; + + if constexpr(terminable) + { + if(!f(std::get(t))) + return false; + } + else f(std::get(t)); + + return rfor_each(t, std::forward(f)); + } + else return true; } -template -constexpr -typename std::enable_if<(i > 0), void>::type +template>() - 1> +constexpr inline bool rfor_each(std::tuple &t, func&& f) { - f(std::get(t)); - rfor_each(t, std::forward(f)); -} - -template -constexpr -typename std::enable_if<(i == -1), void>::type -rfor_each(const std::tuple &t, - func&& f) -{ - constexpr const ssize_t size + if constexpr(i >= 0) { - std::tuple_size>::value - }; + using closure_result = std::invoke_result_t + < + decltype(f), decltype(std::get(t)) + >; - rfor_each(t, std::forward(f)); -} + constexpr bool terminable + { + std::is_same() + }; -template -constexpr -typename std::enable_if<(i == -1), void>::type -rfor_each(std::tuple &t, - func&& f) -{ - constexpr const ssize_t size - { - std::tuple_size>::value - }; + if constexpr(terminable) + { + if(!f(std::get(t))) + return false; + } + else f(std::get(t)); - rfor_each(t, std::forward(f)); + return rfor_each(t, std::forward(f)); + } + else return true; } // -// Iteration of a tuple until() style: your closure returns true to continue, false -// to break. until() then remains true to the end, or returns false if not. - -template -constexpr -typename std::enable_if>::value, bool>::type -until(std::tuple &t, - func&& f) -{ - return true; -} - -template -constexpr -typename std::enable_if>::value, bool>::type -until(const std::tuple &t, - func&& f) -{ - return true; -} - -template -constexpr -typename std::enable_if>::value, bool>::type -until(std::tuple &t, - func&& f) -{ - using value_type = typename std::tuple_element>::type; - return f(static_cast(std::get(t)))? until(t, f) : false; -} - -template -constexpr -typename std::enable_if>::value, bool>::type -until(const std::tuple &t, - func&& f) -{ - using value_type = typename std::tuple_element>::type; - return f(static_cast(std::get(t)))? until(t, f) : false; -} - -// -// Circuits for reverse iteration of a tuple -// -// runtil(tuple, [](auto&& elem) -> bool { ... }); - -template -constexpr -typename std::enable_if::type -runtil(const std::tuple &t, - func&& f) -{ - return true; -} - -template -constexpr -typename std::enable_if::type -runtil(std::tuple &t, - func&& f) -{ - return true; -} - -template -constexpr -typename std::enable_if<(i > 0), bool>::type -runtil(const std::tuple &t, - func&& f) -{ - return f(std::get(t))? runtil(t, f) : false; -} - -template -constexpr typename std::enable_if<(i > 0), bool>::type -runtil(std::tuple &t, - func&& f) -{ - return f(std::get(t))? runtil(t, f) : false; -} - -template -constexpr typename std::enable_if<(i == -1), bool>::type -runtil(const std::tuple &t, - func&& f) -{ - constexpr const auto size - { - std::tuple_size>::value - }; - - return runtil(t, std::forward(f)); -} - -template -constexpr typename std::enable_if<(i == -1), bool>::type -runtil(std::tuple &t, - func&& f) -{ - constexpr const auto size - { - std::tuple_size>::value - }; - - return runtil(t, std::forward(f)); -} - -// -// test() is a logical inversion of until() for intuitive find()-like +// test() is a logical inversion of for_each() for intuitive find()-like // boolean semantics. // -template -constexpr auto -test(std::tuple &t, +constexpr inline auto +test(const std::tuple &t, func&& f) { - return !until(t, [&f](auto&& arg) + return !for_each(t, [&f](const auto &arg) { return !f(arg); }); } -template -constexpr auto -rtest(std::tuple &t, +constexpr inline auto +rtest(const std::tuple &t, func&& f) { - return !runtil(t, [&f](auto&& arg) + return !rfor_each(t, [&f](const auto &arg) { return !f(arg); }); @@ -331,8 +210,7 @@ template -constexpr -typename std::enable_if::type +constexpr typename std::enable_if::type kronecker_delta(const std::tuple &t, func&& f) { @@ -344,8 +222,7 @@ template -constexpr -typename std::enable_if::type +constexpr typename std::enable_if::type kronecker_delta(std::tuple &t, func&& f) { @@ -357,8 +234,7 @@ template -constexpr -typename std::enable_if<(i < j), void>::type +constexpr typename std::enable_if<(i < j), void>::type kronecker_delta(const std::tuple &t, func&& f) { @@ -369,19 +245,16 @@ template -constexpr -typename std::enable_if<(i < j), void>::type +constexpr typename std::enable_if<(i < j), void>::type kronecker_delta(std::tuple &t, func&& f) { kronecker_delta(t, std::forward(f)); } -// -// Get the index of a tuple element by address at runtime -// +/// Get the index of a tuple element by address at runtime template -size_t +inline size_t indexof(tuple &t, const void *const &ptr) { size_t ret(0); @@ -401,12 +274,10 @@ indexof(tuple &t, const void *const &ptr) return ret; } -// -// Tuple layouts are not standard layouts; we can only do this at runtime -// +//// Tuple layouts are not standard layouts; we can only do this at runtime template -off_t +inline off_t tuple_offset(const tuple &t) { return off_t diff --git a/ircd/fmt.cc b/ircd/fmt.cc index a89d282be..29bd5805e 100644 --- a/ircd/fmt.cc +++ b/ircd/fmt.cc @@ -768,9 +768,9 @@ const return ret; }); - return !until(types, [&](auto type) + return test(types, [&](const auto type) { - return !visit_type(val, closure); + return visit_type(val, closure); }); } @@ -854,9 +854,9 @@ const return ret; }); - return !until(types, [&](auto type) + return test(types, [&](const auto type) { - return !visit_type(val, closure); + return visit_type(val, closure); }); } @@ -940,9 +940,9 @@ const return ret; }); - return !until(types, [&](auto type) + return test(types, [&](const auto type) { - return !visit_type(val, closure); + return visit_type(val, closure); }); } @@ -1023,9 +1023,9 @@ const return ret; }); - return !until(types, [&](auto type) + return test(types, [&](const auto type) { - return !visit_type(val, closure); + return visit_type(val, closure); }); } @@ -1106,9 +1106,9 @@ const return ret; }); - return !until(types, [&](auto type) + return test(types, [&](const auto type) { - return !visit_type(val, closure); + return visit_type(val, closure); }); } @@ -1217,9 +1217,9 @@ const return ret; }); - return !until(types, [&](auto type) + return test(types, [&](const auto type) { - return !visit_type(val, closure); + return visit_type(val, closure); }); }