小解C++テンプレート特化


テンプレートの特化(template specialization)は、関数テンプレートの特化とクラステンプレートの特化の2つに分けられます.
(1)関数テンプレートの特化:関数テンプレートが特定のタイプを特別に処理する必要がある場合、関数テンプレートの特化と呼ぶ.例:
bool IsEqual(T t1, T t2)
{
    return t1 == t2;
}

int main()
{
    char str1[] = "Hello";
    char str2[] = "Hello";
    cout << IsEqual(1, 1) << endl;
    cout << IsEqual(str1, str2) << endl;   //  0
return 0;
}

コード11行は文字列が等しいかどうかを比較します.伝達パラメータがchar*タイプであるため、max関数テンプレートは伝達パラメータの値、すなわち2つのポインタが等しいか否かを簡単に比較しただけで、ここでは0を印刷する.明らかに、これは私たちの初心と合わない.したがって、max関数テンプレートはchar*タイプを特別に処理する必要があります.すなわち、特化します.
 template <> bool IsEqual(char* t1, char* t2)           //      
{
      return strcmp(t1, t2) == 0;
}

これにより、Isequal関数のパラメータタイプがchar*の場合、関数テンプレートによってインスタンス化されることなく、Isequal特化バージョンが呼び出されます.
(2)
クラス#クラス#
テンプレートの特化:関数テンプレートと同様に、クラステンプレート内で特定のタイプを特別に処理する必要がある場合に、クラステンプレートの特化を使用します.例:
template <class T>
class compare
{
 public:
 bool IsEqual(T t1, T t2)
 {
      return t1 == t2;
 }
};
  
int main()
{
 char str1[] = "Hello";
 char str2[] = "Hello";
 compare<int> c1;
 compare<char *> c2;   
 cout << c1.IsEqual(1, 1) << endl;        //    int     
 cout << c2.IsEqual(str1, str2) << endl;   //    char *     
 return 0;
}

ここでコード18行もテンプレートクラスcompareを呼び出すIsequalで2つの文字列比較を行い、明らかにここに存在する問題は上記の関数テンプレートと同様に、2つの文字列の内容を比較する必要があり、2つの文字ポインタだけを比較する必要はありません.そのため、クラステンプレートの特化が必要です.
template<>class compare<char *> //  (char*)
{
 public:
    bool IsEqual(char* t1, char* t2)
    {
        return strcmp(t1, t2) == 0;         //  strcmp     
    }
};

注意:クラステンプレートの特化には、すべてのメンバー変数とメンバー関数を特化する必要があります.