引入缘由:编写单一的模板,它能适应大众化,使每种类型都具备相同的功能,但对于某种特定类型,若是要实现其特有的功能,单一模板就没法作到,这时就须要模板特例化。
定义:是对单一模板提供的一个特殊实例,它将一个或多个模板参数绑定到特定的类型或值上。
函数模板特例化:必须为原函数模板的每一个模板参数都提供实参,且使用关键字template后跟一个空尖括号对<>,代表将原模板的全部模板参数提供实参。
template<typename T> //函数模板
int compare(const T &v1,const T &v2) { if(v1 > v2) return -1; if(v2 > v1) return 1; return 0; } //模板特例化,知足针对字符串特定的比较,要提供全部实参,这里只有一个T
template<>
int compare(const char* const &v1,const char* const &v2) { return strcmp(p1,p2); }
特例化版本时,函数参数类型必须与先前声明的模板中对应的类型匹配,其中T为const char*。
本质:特例化的本质是实例化一个模板,而非重载它。特例化不影响参数匹配。参数匹配都以最佳匹配为原则。例如,此处若是是compare(3,5),则调用普通的模板,若为compare(“hi”,”haha”)则调用特例化版本(由于这个cosnt char*相对于T,更匹配实参类型),注意,两者函数体的语句不同了,实现不一样功能。
注意:普通做用于规则使用于特例化,即,模板及其特例化版本应该声明在同一个头文件中,且全部同名模板的声明应该放在前面,后面放特例化版本。
类模板特例化:原理相似函数模板,不过在类中,咱们能够对模板进行特例化,也能够对类进行部分特例化。对类进行特例化时,仍然用template<>表示是一个特例化版本,例如:
template<>
class hash<sales_data> { size_t operator()(sales_data&); //里面全部T都换成特例化类型版本sales_data
};
按照最佳匹配原则,若T != sales_data,就用普通类模板,不然,就使用含有特定功能的特例化版本。
类模板的部分特例化:没必要为全部模板参数提供实参,能够指定一部分而非全部模板参数,一个类模板的部分特例化自己还是一个模板,使用它时还必须为其特例化版本中未指定的模板参数提供实参。此功能就用于STL源码剖析中的traits编程。详见C++primer 628页的例子。(特例化时类名必定要和原来的模板相同,只是参数类型不一样,按最佳匹配原则,那个最匹配,就用相应的模板)
特例化类中的部分红员:能够特例化类中的部分红员函数而不是整个类。
template<typename T>class Foo { void Bar(); void Barst(T a)(); }; template<>
void Foo<int>::Bar() { //进行int类型的特例化处理
} Foo<string> fs; Foo<int> fi;//使用特例化
fs.Bar();//使用的是普通模板,即Foo<string>::Bar()
fi.Bar();//特例化版本,执行Foo<int>::Bar()//Foo<string>::Bar()和Foo<int>::Bar()功能不一样