具有默认模板类型的默认构造函数的类型推导
Type deduction for default constructor with defaulted template type
假设我有这个例子类型:
template < class T = void > struct Test { };
template < > struct Test<void> { };
还有这个类型推导指南:
template<class T> Test() -> Test<T>;
以下编译正常:
Test f;
在 GCC 上。
但是,在 Clang 上。推导指南需为:
template<class T = void> Test() -> Test<T>;
所以我的问题是:哪个是正确的?
默认模板类型应该同时存在于推导和基本类型中,还是仅存在于基本类型中,并假设它会被编译器拾取。
GCC 和 Clang 的主干版本都使用 godbolt.org 使用 -O3 -std=c++17
进行了测试
首先,您实际上不需要此类型的推导指南 - 假设 class 模板参数已经默认。如果你确实提供了推导指南,它应该是:
Test() -> Test<void>;
做推演指南模板没有意义
也就是说,我认为这不是任何一个编译器的错误...。编写具有非推导模板参数的推导指南并没有什么错误,就像您的示例所做的那样:
template<class T> Test() -> Test<T>;
但是,尽管标准允许这种构造,但实际上这样做也没有任何意义。演绎指南的要点是……指导演绎。如果您提供不可扣除的扣除指南,那有什么意义呢?这里的 Clang 错误对我来说似乎很有帮助 - 它提醒您您编写的代码显然是错误的。
如果我们是学究式的,那就是 clang bug。但实际上,我更喜欢 clang 的结果而不是 gcc 的结果。
假设我有这个例子类型:
template < class T = void > struct Test { };
template < > struct Test<void> { };
还有这个类型推导指南:
template<class T> Test() -> Test<T>;
以下编译正常:
Test f;
在 GCC 上。
但是,在 Clang 上。推导指南需为:
template<class T = void> Test() -> Test<T>;
所以我的问题是:哪个是正确的?
默认模板类型应该同时存在于推导和基本类型中,还是仅存在于基本类型中,并假设它会被编译器拾取。
GCC 和 Clang 的主干版本都使用 godbolt.org 使用 -O3 -std=c++17
首先,您实际上不需要此类型的推导指南 - 假设 class 模板参数已经默认。如果你确实提供了推导指南,它应该是:
Test() -> Test<void>;
做推演指南模板没有意义
也就是说,我认为这不是任何一个编译器的错误...。编写具有非推导模板参数的推导指南并没有什么错误,就像您的示例所做的那样:
template<class T> Test() -> Test<T>;
但是,尽管标准允许这种构造,但实际上这样做也没有任何意义。演绎指南的要点是……指导演绎。如果您提供不可扣除的扣除指南,那有什么意义呢?这里的 Clang 错误对我来说似乎很有帮助 - 它提醒您您编写的代码显然是错误的。
如果我们是学究式的,那就是 clang bug。但实际上,我更喜欢 clang 的结果而不是 gcc 的结果。