W.F*_*.F. 9 c++ templates template-templates language-lawyer c++17
又一个decltype(auto)模板模板参数问题.这次我能够创建的最小代码重现错误如下所示:
template <template <decltype(auto)> class TT, decltype(auto) V>
void foo(TT<V>) {
};
template <decltype(auto)>
struct Bar{};
int x;
int main() {
foo(Bar<(x)>{});
}
Run Code Online (Sandbox Code Playgroud)
这在[clang]中导致:
prog.cc:11:5: error: no matching function for call to 'foo'
foo(Bar<(x)>{});
^~~
prog.cc:2:6: note: candidate template ignored: substitution failure [with TT = Bar]: non-type template argument is not a constant expression
void foo(TT<V>) {
^
1 error generated.
Run Code Online (Sandbox Code Playgroud)
[gcc]接受代码.
根据我的理解,代码格式正确,并且clang在解释方面存在错误,但在向lvvm提交错误之前需要确认.我对吗?
根据错误,clang 推导模板template-parameter没有问题,该参数也符合标准 - [temp.arg.template]/3(empasis 是我的):
\n\n\n\n\n当 P 至少与模板参数 A 一样专用时,模板参数与模板参数 P 匹配。如果 P 包含参数包,则如果 A 的每个模板参数都与 P 的模板参数列表中的相应模板参数匹配,则 A 也与 P 匹配。如果两个模板参数\n 匹配,则 A 也与 P 匹配。属于同一类型(类型、非类型、模板),对于非类型\n模板参数,它们的类型是等效的([temp.over.link]),\n 对于模板模板参数,每个它们相应的模板参数以递归方式匹配。当 P 的\n 模板参数列表包含模板参数包时,\n 模板参数包将与 A 的\n 模板参数列表中的零个或多个模板参数或\n 模板参数包匹配\n与P中的模板参数包相同的类型和形式(忽略\n这些模板参数是否是模板参数包)
\n
现在让我们确保Bar<(x)>{}应该推导出 来作为参考。[dcl.type.auto.deduct]/5和[dcl.type.simple]/4涵盖了这一点。
最后让我们检查一下我们是否真的可以使用对带有链接的变量的引用作为模板参数[temp.arg.nontype]/2:
\n\n\n\n\n非类型模板参数的模板参数应为模板参数类型的转换后的常量表达式。\n 对于引用或指针类型的非类型模板参数,\n 的值常量表达式不应引用(或对于指针类型,不应是其地址):
\n\n\n
\n\n- 一个子对象,
\n- 一个临时物体,
\n- 字符串文字,
\n- typeid 表达式的结果,或
\n- 预定义的\xc2\xad \xc2\xadfunc_\xc2\xad_\xc2\xad 变量。
\n[\xe2\x80\x89注意:如果模板参数表示一组重载函数(或指向此类函数的指针或成员指针),则从该集合中选择匹配的函数([over.over])。\xe2\x80\x94\xe2\x80\x89结束注\xe2\x80\x89]
\n
推导的论证满足要求。这使得代码格式良好并暗示了 clang 的错误。
\n\n\n