【转】模板的全特化与偏特化

 

  模板为什么要特化,因为编译器认为,对于特定的类型,如果你能对某一功能更好地实现,那么就该听你的。

  模板分为类模板与函数模板,特化分为全特化与偏特化。全特化就是限定死模板实现的具体类型,偏特化就是如果这个模板有多个类型,那么只限定其中的一部分。

 

先看类模板:

 1 #include <iostream>
 2 using namespace std;
 3 
 4 template<class T1, class T2> class Test
 5 {
 6 public:
 7     Test(T1 i, T2 j) :a(i), b(j) { cout << "类模板" << endl; }
 8 private:
 9     T1 a;
10     T2 b;
11 };
12 
13 template<> class Test<int, char>
14 {
15 public:
16     Test(int i, char j) :a(i), b(j) { cout << "全特化" << endl; }
17 private:
18     int a;
19     char b;
20 };
21 
22 template<class T2> class Test<char, T2>
23 {
24 public:
25     Test(char i, T2 j) :a(i), b(j) { cout << "偏特化" << endl; }
26 private:
27     char a;
28     T2 b;
29 };
30 
31 
32 int main()
33 {
34     Test<double, double> t1(1.4, 2.3);    //这是类模板
35     Test<int, char> t2(5, 'A');    //这是全特化
36     Test<char, float> t3('B', 3.1);    //这是偏特化
37 
38     return 0;
39 }

  请注意,必须要先有类模板,才能定义类模板的全特化和偏特化。

而对于函数模板,却只有全特化,不能偏特化:

 1 //模板函数
 2 template<typename T1, typename T2>
 3 void fun(T1 a, T2 b)
 4 {
 5     cout << "模板函数" << endl;
 6 }
 7 
 8 //全特化
 9 template<>
10 void fun<int, char >(int a, char b)
11 {
12     cout << "全特化" << endl;
13 }
14 
15 //函数不存在偏特化:下面的代码是错误的
16 //提示非法使用显示模板参数
17 /*
18 template<typename T2>
19 void fun<char,T2>(char a, T2 b)
20 {
21 cout<<"偏特化"<<endl;
22 }
23 */
24 
25 int main()
26 {
27     fun(1, 3.14);    //函数模板
28     fun(2, 'B');    //函数模板的全特化
29 
30     return 0;
31 }

  至于为什么函数不能偏特化,似乎不是因为语言实现不了,而是因为偏特化的功能可以通过函数的重载完成。

 

为什么需要使用模板的特化呢?

  因为有时需要对某些类型进行特别处理,不然会出错。

例如:

 1 #include <iostream>
 2 using namespace std;
 3 //函数模板
 4 template<class T>
 5 bool IsEqual(T t1, T t2) {
 6     return t1 == t2;
 7 }
 8 
 9 template<> //函数模板特化
10 bool IsEqual(char *t1, char *t2) {
11     return strcmp(t1, t2) == 0;    //因为不能像函数模板一样使用"=="来判断两个字符串是否相等,所以需要特化
12 }
13 
14 //类模板
15 template<class T>
16 class compare {
17 public:
18     bool IsEqual(T t1, T t2) {
19         return t1 == t2;
20     }
21 };
22 
23 //类模板的特化
24 template<>
25 class compare<char*> {
26 public:
27     bool IsEqual(char *t1, char *t2) {
28         return strcmp(t1, t2) == 0;    //因为不能像类模板中一样使用"=="来判断两个字符串是否相等,所以需要特化
29     }
30 };
31 int main()
32 {
33     char str1[] = "abc";
34     char str2[] = "abc";
35     cout << "函数模板和函数模板特化" << endl;
36     cout << IsEqual(1, 1) << endl;
37     cout << IsEqual(str1, str2) << endl;
38     compare<int> c1;
39     compare<char*> c2;
40     cout << "类模板和类模板特化" << endl;
41     cout << c1.IsEqual(1, 1) << endl;
42     cout << c2.IsEqual(str1, str2) << endl;
43     getchar();
44     return 0;
45 }

 

转自:

  1、http://blog.csdn.net/thefutureisour/article/details/7964682/

  2、http://blog.csdn.net/zhuimengzh/article/details/6838886

posted @ 2017-07-28 15:32  阿玛尼迪迪  阅读(333)  评论(0编辑  收藏  举报