Sum*_*ood 6 c++ variadic-templates c++17
考虑下面的C++ 17代码,该代码测试一组枚举值以查看该集合中是否包含另一个枚举值:
enum Flag { val1, val2, val3, val4, val5 };
template<Flag arg> struct Value {
template<Flag... set> struct IsIn {
static constexpr bool value =
static_cast<bool>(((set == arg) || ...));
};
};
Run Code Online (Sandbox Code Playgroud)
这按预期工作:
bool x = Value<val4>::IsIn<val1, val2, val5>::value;
// x == false
bool y = Value<val2>::IsIn<val3, val2>::value;
// y == true
Run Code Online (Sandbox Code Playgroud)
但是,我希望测试是否所有一组值都包含在另一个集合中,如下所示:
template<Flag... args> struct Values {
template<Flag... set> struct AreIn {
static constexpr bool value =
static_cast<bool>((Value<args>::IsIn<set...>::value && ...));
};
};
Run Code Online (Sandbox Code Playgroud)
以上内容不适用于GCC 7.3或Clang 5.0; 他们都给出了相当神秘的答案,这些答案几乎无法洞察问题.鉴于允许模板参数列表中的参数包扩展(只要模板支持扩展),我很难弄清楚为什么这不是合法的C++.
您遇到了C++语法中最令人烦恼的问题之一:不可推断的依赖名称.
当你这样做Foo<Bar>::Baz<Quux>,因为Foo<Bar>是一个从属名称,你必须先放置template关键字Baz,以防止解析器在悬崖上运行.Clang 通常非常擅长用一个有用的错误明确地告诉你这个,但在某些情况下(比如你的)它只是爆炸并且说Expected )或者同样无益的东西.
有关更多信息,请参阅此其他问题
因此,您需要做的就是修复模板,template在依赖模板调用上添加关键字:
template<Flag... args>
struct Values {
template<Flag... set>
struct AreIn {
static constexpr bool value =
static_cast<bool>((Value<args>::template IsIn<set...>::value && ...));
};
};
Run Code Online (Sandbox Code Playgroud)
另请注意,这static_cast<bool>()是多余的.
| 归档时间: |
|
| 查看次数: |
408 次 |
| 最近记录: |