c++ - sfinae 检测容器:std:array 失败
问题描述
我正在寻找一种使用 SFINAE 实现某些功能的方法,该功能必须仅对某些容器可用:向量、列表、数组(下面的集合仅作为测试)
在这个答案的基础上,我尝试了下面的代码,它使用了一个仅对所需容器返回 true 的特征类。
正如您在此处在线看到的那样,它失败了std::array
。
template <typename Container>
struct is_container : std::false_type { };
template <typename... Ts> struct is_container<std::array<Ts... >> : std::true_type { };
template <typename... Ts> struct is_container<std::vector<Ts...>> : std::true_type { };
template <typename... Ts> struct is_container<std::set<Ts... >> : std::true_type { };
template <typename... Ts> struct is_container<std::list<Ts... >> : std::true_type { };
template <typename... Ts> struct Dummy{};
int main()
{
std::cout << "Dummy: " << is_container<Dummy<int>>::value << '\n';
std::cout << "array: " << is_container<std::array<int,5>>::value << '\n';
std::cout << "vector:" << is_container<std::vector<int>>::value << '\n';
std::cout << "set: " << is_container<std::set<int>>::value << '\n';
std::cout << "list: " << is_container<std::list<int>>::value << '\n';
}
我的理解是,这是因为std::array
需要第二个模板参数。我对可变参数模板的经验很少,所以我的问题是:
有没有办法使这种方法成功? 还是我应该使用链接问题中描述的另一种方法?
我宁愿拥有纯 C++11 的东西,但 C++14 也可以。
解决方案
这不是 SFINAE,而是常规模板专业化。您的 std::array 无法识别,因为 std::size_t 类型的值(即 std::array 的第二个参数)不是类型名。
您可以专门更改对数组的检查:
template <typename T, std::size_t N> struct is_container<std::array<T,N>> : std::true_type { };
template <typename... Ts> struct is_container<std::vector<Ts...>> : std::true_type { };
如果您真的想使用SFINAE检查任何行为类似于容器的东西,您可以检查该类型是否存在 std::begin、std::end、std::size。
推荐阅读
- ada - 如何调试 Ada 程序?
- android - 处理导航返回按钮
- sql-server - 为什么我不能使用 VS 2019 社区在 SQL Server 2019 中创建边缘约束
- ruby-on-rails - 如何将 CoreUI 合并到 React Rails 应用程序中?
- machine-learning - 如何调试数学方程的实现
- objective-c - NSDocument 窗口关闭后如何释放内存?
- firebase - 在 Firebase 实时规则中翻转 OR 条件返回错误访问
- python - 使用 python 客户端使用客户端证书访问 K8S API
- javascript - Firebase 托管上的 MP4 视频在 Chrome 上不规则地加载
- bash - bash 函数中的 printf 向 `wc -l` 结果添加新行