默认模板参数部分专业化
请向我解释为什么下面的一段代码符合并完美地工作。 我很困扰。
#include<iostream> template<class A = int, class B=double> class Base {}; template<class B> class Base <int, B> { public: Base() { std::cout<<"it works!!!!!\n"; } }; int main() { Base<> base; // it prints "it works!!!!!" return 0; }
它不应该落入模板类Base的一般forms吗?
默认参数适用于专业化 – 事实上,专业化必须接受(可以这么说)基本模板的默认参数。 试图在专门化中指定一个默认值:
template<class A = int, class B=double> class Base {}; template<class B=char> // ...
…是一个错误。
同样,如果我们改变专门化,使其专业化为基础模板提供的默认types以外的其他types:
template<class A = int, class B=double> class Base {}; template<class B> class Base <char, B>
…然后select基础模板。
所以,发生了什么事情是这样的:首先select模板参数的types。 在这种情况下(在实例化时没有指定types),这两种types都基于基本模板中指定的默认模板参数。
然后(作为一个基本上单独的步骤),它执行所有符合这些参数types的模板的重载parsing模拟。 像重载parsing一样,明确指定的types优于隐式指定的types,因此您的专用化(明确指定int
)优先于基本模板(隐式指定int
)。
template<class A = int, class B=double> class Base {};
这里A和B的默认值/初始值分别被声明为int和double。
template<class B> class Base <int, B>
在类定义中,第一个参数类似于一个常量值(这里是int;为什么用这种方式使事情变得复杂?最好删除第一个模板参数),第二个模板参数是B,默认值是'double'。
Base<> base;
当你创build类的对象。 虽然不指定模板参数,但是编译器使用“int”和“double”参数的默认值(A和B),并且代码执行时没有任何错误或警告。
看看当你创build对象时会发生什么:
Base<float,char> b;
或者Base<char,char> b;
当你写Base<> base;
编译器会试图找出Base<>
类的实例是否可能,如果有可能的话代码可以正常工作。 在这种情况下,可能由于Base的默认模板参数,因为编译器知道如果您编写Base<>
它需要创buildBase<int,double>
的对象。 即:因为:
template<class A = int, class B=double> class Base {};
所以代码工作正常。