此问题在此处已有答案:
Can you use a braced-init-list as a (default) template argument?(2个答案)
21天前关闭
编辑:这个问题已经三年了,怎么会是昨天问的另一个问题的重复呢?
我的印象是,以下代码应该成为新C++20标准下的有效代码:
struct Foo
{
int a, b;
};
template<Foo>
struct Bar
{};
Bar<{.a=1, .b=2}> bar;
字符串
然而,gcc 10.2.0
,设置了-std=c++20
,抱怨说:could not convert ‘{1, 2}’ from ‘<brace-enclosed initializer list>’ to ‘Foo’
和Clang也不能编译这个片段。有人能指出为什么它格式不好吗?
2条答案
按热度按时间p8h8hvxi1#
这个模板参数
字符串
根据只允许以下结构的模板参数的语法,不允许:
template-argument:
constant-expression
类型id
ID表达式
大括号初始化列表不是上面的任何一个结构,它实际上是一个初始化器,因此不能用作模板参数。
你可以明确地指出你用作template-argument的对象的类型:
型
这是可行的,因为这是一个常数表达式。
n3ipq98p2#
这是一个C语法的东西。模板参数使用的东西必须是类型id,id名称,或常量表达式。
花括号初始化列表不是任何类型的表达式,它们只能在语法上出现在少数地方,特别是那些用于初始化对象或变量的地方。
在过去,这并不重要,因为没有太多的理由使用花括号初始化列表来初始化几个有效的NTTP。显然,这已经改变了,所以这是一个疏忽。但这是C20标准所说的。