1. 程式人生 > >C++模板全特化、偏特化

C++模板全特化、偏特化

https://blog.csdn.net/m_buddy/article/details/72973207

 

1. C++模板

大家都對C++的模板程式設計應該都能很熟練使用了,下面就是一段很簡單不過的例子了

    //模板函式
    template<typename T, class N> void func(T num1, N num2)
    {
        cout << "num1:" << num1 << ", num2:" << num2 <<endl;
    }
     
    //模板類
    template<typename T, class N> class Test_Class
    {
        static bool comp(T num1, N num2)
        {
            return (num1<num2)?true:false;
        }
    };

2. C++模板全特化

特化其實就是特殊化的意思,在模板類裡,所有的型別都是模板(template<class T>),而一旦我們將所有的模板型別T都明確化,並且寫了一個類名與主模板類名相同的類,那麼這個類就叫做全特化類。C++模板全特化之後已經失去了Template的屬性了。

示例

    //模板函式
    template<typename T, class N> void func(T num1, N num2)
    {
        //cout << "num1:" << num1 << ", num2:" << num2 <<endl;
    }
     
    //模板類
    template<typename T, class N> class Test_Class
    {
    public:
        static bool comp(T num1, N num2)
        {
            return (num1<num2)?true:false;
        }
    };
     
    //全特化,模板函式
    template<> void func(int num1, double num2)
    {
        cout << "num1:" << num1 << ", num2:" << num2 <<endl;
    }
     
    //全特化,模板類
    template<> class Test_Class<int, double>
    {
    public:
        static bool comp(int num1, double num2)
        {
            return (num1<num2)?true:false;
        }
    };

呼叫

    func<int, double>(1, 2.0);
    Test_Class<int, double>::comp(1, 2.0);

注意:一個模板被稱為全特化的條件:1.必須有一個主模板類  2.模板型別被全部明確化
3. C++模板偏特化

上面對主版本模板和全特化進行了定義,那麼偏特化就是介於二者之間的模板,它的模板名與主版本模板名相同,但是它的模板型中,有被明確化的部分和沒有被明確化的部分。

示例

    //模板函式
    template<typename T, class N> void func(T num1, N num2)
    {
        //cout << "num1:" << num1 << ", num2:" << num2 <<endl;
    }
     
    //模板類
    template<typename T, class N> class Test_Class
    {
    public:
        static bool comp(T num1, N num2)
        {
            return (num1<num2)?true:false;
        }
    };
     
    //偏特化,模板函式
    template<class N> void func(int num1, N num2)
    {
        cout << "num1:" << num1 << ", num2:" << num2 <<endl;
    }
     
    //偏特化,模板類
    template<class N> class Test_Class<int, N>
    {
    public:
        static bool comp(int num1, double num2)
        {
            return (num1<num2)?true:false;
        }
    };

呼叫

    func<int, double>(1, 2.0);
    Test_Class<int, double>::comp(1, 2.0);

注意:偏特化的條件:1.必須有一個主模板   2.模板型別被部分明確化

4. 模板類呼叫優先順序

對主版本模板類、全特化類、偏特化類的呼叫優先順序從高到低進行排序是:全特化類>偏特化類>主版本模板類。這樣的優先順序順序對效能也是最好的。

但是模板特化並不只是為了效能優化,更多是為了讓模板函式能夠正常工作,最典型的例子就是STL中的iterator_traits。algorithm中大多數演算法通過iterator物件來處理資料,但是同時允許以指標代替iterator物件,這是為了支援C-Style Array。如果直接操作iterator,那麼為了支援指標型別,每個函式都需要進行過載,因為指標沒有::value_type型別。為了解決這個問題,STL使用了iterator_traits,併為指標型別進行轉化,演算法通過它來操作iterator,不需要知道實際操作的是iterator物件還是指標。

    template<typename IteratorClass> class iterator_traits
    ...
    template<typename ValueType> class iterator_traits<ValueType*>
    ...
    template<typename ValueType> class iterator_traits<ValueType const*>
    ...

後面兩是針對指標型別的偏特化,也是偏特化的一種常見形式。


 
---------------------  
作者:m_buddy  
來源:CSDN  
原文:https://blog.csdn.net/m_buddy/article/details/72973207  
版權宣告:本文為博主原創文章,轉載請附上博文連結!