std::has_single_bit 是 C++20 引入的 constexpr 函数,用于判断整数是否为 2 的幂(非零),要求包含 头文件并启用 C++20 标准。

std::has_single_bit 是 C++20 新增的 constexpr 工具函数,专用于判断一个整数是否为 2 的幂(且非零)
它不处理负数、零或浮点数,只对无符号整型或有符号整型的非负值有意义。底层逻辑是检查该数的二进制表示中是否**恰好只有一个 bit 被置为 1**——这正是 2 的幂(1, 2, 4, 8, 16…)的数学本质。
注意:std::has_single_bit 不是宏也不是模板特化技巧,它是标准库提供的头等公民函数,定义在 头文件中。
必须包含 并确保编译器支持 C++20
常见错误是忘记包含头文件,或在不支持 C++20 的模式下编译,此时会报错:‘has_single_bit’ is not a member of ‘std’ 或 unknown type name 'has_single_bit'。
- Clang/GCC 需加
-std=c++20(-std=gnu++20也可) - MSVC 需用 /std:c++20(VS 2019 16.10+ 或 VS 2022)
- 不能用
或替代
最小可运行示例:
立即学习“C++免费学习笔记(深入)”;
#include#include int main() { std::cout << std::has_single_bit(8u) << "\n"; // 1 std::cout << std::has_single_bit(0u) << "\n"; // 0 std::cout << std::has_single_bit(5u) << "\n"; // 0 std::cout << std::has_single_bit(1u) << "\n"; // 1 }
和 (x & (x-1)) == 0 的传统写法有何区别?
两者数学等价,但语义与保障不同:
-
(x & (x-1)) == 0对x == 0也返回 true,需额外判断x != 0;而std::has_single_bit(x)**天然排除 0**,语义更精确 -
std::has_single_bit是constexpr、noexcept、支持所有整型(包括std::byte),且编译器可内联优化为单条指令(如 x86 的blsi+ test) - 对有符号类型(如
int),若值为负,行为未定义;建议统一用无符号类型(unsigned int,uint64_t)传入
实际使用时最容易忽略的边界情况
不是所有“看着像 2 的幂”的数都满足条件:
-
std::has_single_bit(1)→ true(2⁰) -
std::has_single_bit(0)→ false(明确排除) -
std::has_single_bit(-1)→ 未定义行为(不要传负数) -
std::has_single_bit(0x80000000u)→ true(在 32 位 unsigned 中是 2³¹) - 对
char或short,会先整型提升,但结果仍符合预期;不过显式用uint32_t等更安全
如果你在做内存对齐检查、哈希表容量校验或位掩码有效性验证,直接用 std::has_single_bit 比手写位运算更不易出错——前提是别忘了它只回答“是不是 2 的幂”,不负责帮你找那个幂次是多少。










