23template <aui::
unsigned_
integral T>
24 requires(!aui::same_as<T, bool>) && (!aui::same_as<T, char>) && (!aui::same_as<T, char8_t>) &&
25 (!aui::same_as<T, char16_t>) && (!aui::same_as<T, char32_t>) && (!aui::same_as<T, wchar_t>)
26constexpr T bit_width(T x)
noexcept {
27 return std::numeric_limits<T>::digits - std::countl_zero(x);
30template <aui::
unsigned_
integral T>
31 requires(!aui::same_as<T, bool>) && (!aui::same_as<T, char>) && (!aui::same_as<T, char8_t>) &&
32 (!aui::same_as<T, char16_t>) && (!aui::same_as<T, char32_t>) && (!aui::same_as<T, wchar_t>)
33constexpr T bit_ceil(T x)
noexcept {
36 if constexpr (aui::same_as<T,
decltype(+x)>)
37 return T(1) << aui::bit_width(T(x - 1));
39 constexpr int offset_for_ub = std::numeric_limits<unsigned>::digits - std::numeric_limits<T>::digits;
40 return T(1u << (aui::bit_width(T(x - 1)) + offset_for_ub) >> offset_for_ub);
44template <aui::
unsigned_
integral T>
45 requires(!std::same_as<T, bool>) && (!std::same_as<T, char>) && (!std::same_as<T, char8_t>) &&
46 (!std::same_as<T, char16_t>) && (!std::same_as<T, char32_t>) && (!std::same_as<T, wchar_t>)
47constexpr T bit_floor(T x)
noexcept {
49 return T { 1 } << (aui::bit_width(x) - 1);