如何在函数参数中强制执行类型并避免隐式转换?
How to enforce type in function params and avoid implicit conversion?
我有一个功能
template<typename T>
static inline bool Contains(T container, const typename T::value_type& value)
{
return std::find(container.begin(), container.end(), value) != container.end();
}
是否有禁止此函数隐式转换的选项?
此代码编译失败:
std::vector<int> vec = {1, 2, 3};
Contains(vec, -5.2);
在这个 post How do I avoid implicit conversions on non-constructing functions? 中,他们完全删除了某些类型的使用,但事实并非如此。
谢谢。
template<typename x_Container, typename x_Value>
static inline bool Contains(x_Container const & container, x_Value const & value)
{
static_assert(::std::is_same_v<typename x_Container::value_type, x_Value>);
return std::find(container.begin(), container.end(), value) != container.end();
}
您可以在函数中添加第二个模板参数和一个 static_assert 以确保第二个参数与容器的值类型完全相同。
template<typename T, typename U>
static inline bool Contains(const T& container, const U& value)
{
static_assert(std::is_same_v<typename T::value_type, U>, "NO IMPLICIT CONVERSION ALLOWED");
return std::find(container.begin(), container.end(), value) != container.end();
}
int main() {
std::vector<int> vec = {1, 2, 3};
Contains(vec, -5.2); // Fails now
}
完整示例 here.
在C++20中,就这么简单:
template<typename T>
static inline bool Contains(T container, std::same_as<typename T::value_type> auto const& value)
{
return std::find(container.begin(), container.end(), value) != container.end();
}
在这段代码中std::same_as
是一个概念,可以与简洁的模板语法一起使用。
此解决方案的一个优点是编译器错误发生在调用站点,告诉用户参数类型错误。
我有一个功能
template<typename T>
static inline bool Contains(T container, const typename T::value_type& value)
{
return std::find(container.begin(), container.end(), value) != container.end();
}
是否有禁止此函数隐式转换的选项?
此代码编译失败:
std::vector<int> vec = {1, 2, 3};
Contains(vec, -5.2);
在这个 post How do I avoid implicit conversions on non-constructing functions? 中,他们完全删除了某些类型的使用,但事实并非如此。
谢谢。
template<typename x_Container, typename x_Value>
static inline bool Contains(x_Container const & container, x_Value const & value)
{
static_assert(::std::is_same_v<typename x_Container::value_type, x_Value>);
return std::find(container.begin(), container.end(), value) != container.end();
}
您可以在函数中添加第二个模板参数和一个 static_assert 以确保第二个参数与容器的值类型完全相同。
template<typename T, typename U>
static inline bool Contains(const T& container, const U& value)
{
static_assert(std::is_same_v<typename T::value_type, U>, "NO IMPLICIT CONVERSION ALLOWED");
return std::find(container.begin(), container.end(), value) != container.end();
}
int main() {
std::vector<int> vec = {1, 2, 3};
Contains(vec, -5.2); // Fails now
}
完整示例 here.
在C++20中,就这么简单:
template<typename T>
static inline bool Contains(T container, std::same_as<typename T::value_type> auto const& value)
{
return std::find(container.begin(), container.end(), value) != container.end();
}
在这段代码中std::same_as
是一个概念,可以与简洁的模板语法一起使用。
此解决方案的一个优点是编译器错误发生在调用站点,告诉用户参数类型错误。