我有一个带有几个强类型枚举的类,我希望它们与int隐式可比。为此,我编写了超简单的模板函数:
template<class T> bool operator==(const T &e, const int &i)
{
return (static_cast<int>(e) == i);
}
而另一对
template<class T> bool operator==(const int &i, const T &e)
{
return (e == i);
}
但是,这可能很危险,因为它几乎为空白类T和整数之间的比较写了一个空白检查。因此,我只需要几个明确指定的实例,例如
template bool operator==(const MyEnum &e, const int &i);
template bool operator==(const int &i, const MyEnum &e);
没有其他。有没有办法禁用所有隐式实例化或实现此目的?当然,我总是可以为每个枚举分别编写两个运算符,但是模板确实看起来是一个更好的解决方案。
最佳答案
使用SFINAE拒绝不会推断出MyEnum
的重载:
template<class T, std::enable_if_t<std::is_same<T, MyEnum>::value>* = nullptr>
bool operator==(const T &e, const int &i);
template<class T, std::enable_if_t<std::is_same<T, MyEnum>::value>* = nullptr>
bool operator==(const int &i, const T &e);
由于评论,我更新了我的答案。如果您只想接受选择几种模板类型,那么我建议使用此
bool_or
技巧:#include <type_traits>
#include <utility>
template<bool... Bs>
using bool_sequence = std::integer_sequence<bool, Bs...>;
template<bool... Bs>
using bool_and = std::is_same<bool_sequence<Bs...>,
bool_sequence<(Bs || true)...>>;
template<bool... Bs>
using bool_or = std::integral_constant<bool, !bool_and<!Bs...>::value>;
template<class T, class... Ts>
using any_same = bool_or<std::is_same<T, Ts>::value...>;
template<class T, std::enable_if_t<any_same<T, MyEnum, X, Y, Z>::value>* = nullptr>
bool operator==(const T &e, const int &i);
template<class T, std::enable_if_t<any_same<T, MyEnum, X, Y, Z>::value>* = nullptr>
bool operator==(const int &i, const T &e);
您可以添加任意数量的类型进行比较。
关于c++ - 如何防止模板函数的隐式实例化,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/32288371/