下面经过简化的代码在最新版本的clang++5中无法工作,但被g++7接受:
然而,如果我将类模板定义中的默认模板参数
我尝试阅读标准措辞,但对于这种特定情况并没有很大的帮助。当生成虚构函数模板时,只使用前向声明中的默认模板参数是预期的行为,还是这是编译器的一个错误?
template<typename Wrapped, typename U>
struct wrapper;
template<typename Wrapped, typename U=int>
struct wrapper
{
wrapper() = default;
// Automatic deduction guide
constexpr explicit wrapper(Wrapped) noexcept {}
};
int main()
{
struct {} dummy;
constexpr auto wrapped = wrapper(dummy);
}
以下是出现的错误信息:
<source>:18:30: error: no viable constructor or deduction guide for deduction of template arguments of 'wrapper'
constexpr auto wrapped = wrapper(dummy);
^
<source>:12:24: note: candidate template ignored: couldn't infer template argument 'U'
constexpr explicit wrapper(Wrapped) noexcept {}
^
<source>:4:8: note: candidate template ignored: could not match 'wrapper<Wrapped, U>' against '(anonymous struct at <source>:17:5)'
struct wrapper;
^
<source>:9:5: note: candidate function template not viable: requires 0 arguments, but 1 was provided
wrapper() = default;
^
然而,如果我将类模板定义中的默认模板参数
=int
移到前向声明中,一切都能完美运行(U
按预期被推导为int
),好像只有在前向声明中的默认模板参数被考虑进用于推导指南的虚构函数模板集合时才会生效。我尝试阅读标准措辞,但对于这种特定情况并没有很大的帮助。当生成虚构函数模板时,只使用前向声明中的默认模板参数是预期的行为,还是这是编译器的一个错误?
template <class Wrapper> wrapper(Wrapper) -> wrapper<Wrapper>;
- W.F.