zoukankan      html  css  js  c++  java
  • 【转】模板的全特化与偏特化

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

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

    先看类模板:

     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

  • 相关阅读:
    用存储过程实现二进制字段的更新
    在Google 上搜书的方法 (转)
    Oracle开发中,关于查询的一个问题
    北京公司招聘 .net开发人员
    UIAlertView的使用方法
    FMEFB开始上传
    应用中的安全管理方案
    使用NHibernate时需要考虑的另一个问题
    .net使用Com组件的问题
    使用NHibernate时,如何提高访问Oracle数据库(ODP.net)的性能
  • 原文地址:https://www.cnblogs.com/codingmengmeng/p/7250552.html
Copyright © 2011-2022 走看看