<>
有充分的理由吗?在指定一个所有模板参数都有默认值的模板类时是必需的吗?
例如
#include <iostream>
template<typename T = int>
class C {
public:
T obj = 0;
};
int main()
{
C c1; // Error on almost all compilers (see note below)
C<> c2;
std::cout << c1.obj << " " << c2.obj << std::endl;
return 0;
}
这样做的一个缺点是,如果你有一个已经在不同地方使用的类,你后来将它重构为一个类模板,它的模板参数有默认参数,那么你必须添加 <>
在所有使用该类的地方。
注意:它看起来像 GCC 最新的 HEAD (7.0.1) accepts没有 <>
的语法.早期版本没有,任何版本的 Clang 也没有。这是最新的 GCC HEAD 中的错误吗?或者也许 C++17 的标准现在接受没有 <>
的语法GCC 就在前面?
最佳答案
在 C++17 中,这是良构的:
C c1{};
由于deduction for class templates .我们将为每个构造函数(和推导指南)合成一个函数并执行重载解析:
template <class T=int> C<T> foo();
template <class T=int> C<T> foo(C<T> const&);
template <class T=int> C<T> foo(C<T>&&);
第一个是可行的重载,另外两个不是,所以推导成功,占位符C
被推导类型取代 C<int>
.
但是,从语法上讲,[dcl.type.class.deduct] 中需要初始化器:
If a placeholder for a deduced class type appears as a decl-specifier in the decl-specifier-seq of a simple-declaration, the init-declarator of that declaration shall be of the form:
declarator-id attribute-specifier-seqopt initializer
The placeholder is replaced by the return type of the function selected by overload resolution for class template deduction (13.3.1.8).
但是 显然,此限制已在 Kona 中解除,因此 C c;
不包含初始化器,因此它不符合语法。这是允许这样做的 gcc 错误。尽管明确禁止这一点似乎很奇怪。C c;
在 C++17 中确实是良构的。一旦出现新的措辞,我将更新答案。
在 C++17 之前,语句格式错误仅仅是因为 C
不是一种类型。 C
和 C<>
不是一回事。对于拥有所有默认模板参数,过去和现在都没有特别考虑。类型和类模板是不同的,并且继续被区别对待。
关于c++ - 为什么 <> 在指定一个所有模板参数都有默认值的模板类时是必需的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42670137/