C++如何实现void方法自动识别适配不同位数uint类型参数
实现方案
不需要为每种无符号整数写重载,用带类型约束的函数模板即可实现自动识别传入的无符号整数类型,同时可以拦截非法的非无符号整数传参,根据使用的C++标准选对应写法即可。
C++20及以上版本(推荐)
用标准库自带的std::unsigned_integral概念做类型约束,代码最简洁直观:
- 把原来头文件里的单参数声明替换为模板声明,模板实现直接放在头文件中(模板不支持分离编译,不要把实现单独写在cpp里)
#include <cstdint> #include <concepts> #include <type_traits> class Message_Test { public: template<std::unsigned_integral T> void Integers(const T& _value) { // 此处T就是传入参数的实际类型,可直接做分支判断 if constexpr (std::is_same_v<T, uint16_t>) { // 写入uint16_t类型对应的专属处理逻辑 } else if constexpr (std::is_same_v<T, uint32_t>) { // 写入uint32_t类型对应的专属处理逻辑 } else if constexpr (std::is_same_v<T, uint64_t>) { // 写入uint64_t类型对应的专属处理逻辑 } // 所有无符号整数的公共处理逻辑直接写在分支外即可 // _value会自动匹配传入的实际类型,无隐式转换开销 } };
这种写法支持所有标准无符号整数类型传入,包括uint8_t、uint16_t、uint32_t、uint64_t以及原生的unsigned int、unsigned long等,编译器会在编译期自动识别传入参数类型,生成对应版本的函数实例,运行时没有额外开销。
C++11/14/17 版本
如果编译器不支持C20的concept特性,用SFINAE规则做类型约束即可,内部类型判断逻辑和C20版本完全一致:
#include <cstdint> #include <type_traits> class Message_Test { public: template<typename T, typename = std::enable_if_t<std::is_unsigned_v<T>>> void Integers(const T& _value) { // 类型判断、业务逻辑写法和上面C++20版本完全相同 if constexpr (std::is_same_v<T, uint16_t>) { // uint16_t专属逻辑 } // 其余分支、公共逻辑同上 } };
注意:C17之前的版本不支持
if constexpr,判断类型需要用模板特化或者标签分发的方式实现分支逻辑,优先推荐升级到C17及以上版本简化代码。
避坑提醒
不要为了省事直接保留const uint64_t&的参数定义,这种写法虽然可以通过隐式类型转换接收更小位宽的无符号整数,但函数内部拿到的永远是uint64_t类型,根本无法识别传入参数的原始类型,满足不了自动识别类型的需求。
内容的提问来源于stack exchange,提问作者Ricardoke
相关产品推荐
相关产品推荐

