C++模板特化

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

模板为什么要特化,因为编译器认为,对于特定的类型,如果程序员能对某一功能更好的实现,那么就按照程序员的思路办。

全特化: 将模板参数列表中所有的参数都确切化

template <typename T>
class SeqList{
public:
    SeqList();
    ~SeqList();
private:
    int _size;
    int _capacity;
    T* _data;
};
template <typename T>
SeqList<T>::SeqList()
            :_size(0)
            ,_capacity(10)
            ,_data(new T[_capacity]) {
    std::cout << "SeqList<T>" << std::endl;
}

template <typename T>
SeqList<T>::~SeqList() {
    delete []_data;
}
//全特化 int类型
template <>
class SeqList <int> {
public:
    SeqList(int capacity);
    ~SeqList();
private:
    int _size;
    int _capacity;
    int* _data;
};
//特化后定义成员函数不再需要模板形参
SeqList<int>::SeqList(int capacity)
            :_size(0)
            ,_capacity(capacity)
            ,_data(new int[_capacity]){
    std::cout << "SeqList<int>" << std::endl;
}
//特化后定义成员函数不再需要模板形参
SeqList<int>::~SeqList(){
    delete []_data;
}
void test1(){
    SeqList<float> sl2; //函数模板
    SeqList<int> sl1(5); //全特化
}

偏特化: 任何针对模板形参进一步进行条件限制设计的特化版本

1)局部参数特化:

template <typename T1, typename T2>
class Data {
public:
    Data(T1 d1,T2 d2);
private:
    T1 _d1;
    T2 _d2;
};
template <typename T1, typename T2>
Data<T1,T2>::Data(T1 d1,T2 d2)
            :_d1(d1)
            ,_d2(d2){
    std::cout << "Data<T1,T2>" << std::endl;
}
//局部特化第二个参数
template <typename T1>
class Data <T1,int> {
public:
    Data(T1 d1,int d2);
private:
    T1 _d1;
    int _d2;
};
template <typename T1>
Data<T1,int>::Data(T1 d1,int d2)
            :_d1(d1)
            ,_d2(d2) {
    std::cout << "Data<T1,int>" << std::endl;
}
void test2(){
    Data<float,int> d1(1.2,1); //局部参数特化
    Data<int,int> d2(1,1);     //局部参数特化
    Data<float,float> d3(1.2,1.3); //非特化模板
}

在实例化类的时候,当在局部特化的位置上出现与之对应的类型,那么直接调用该局部特化版本。

2)局部特化两个参数为指针类型/引用

// 局部特化两个参数为指针类型
template <typename T1, typename T2>
class Data <T1*, T2*>
{
public :
     Data();
private :
     T1 _d1 ;
     T2 _d2 ;
     T1* _d3 ;
     T2* _d4 ;
};
template <typename T1, typename T2>
Data<T1 *, T2*>:: Data()
{
     cout<<"Data<T1*, T2*>" <<endl;
}
 
// 局部特化两个参数为引用
template <typename T1, typename T2>
class Data <T1&, T2&>
{
public :
     Data(const T1& d1, const T2& d2);
private :
     const T1 & _d1;
     const T2 & _d2;
     T1* _d3 ;
     T2* _d4 ;
};
template <typename T1, typename T2>
Data<T1 &, T2&>:: Data(const T1& d1, const T2& d2)
             : _d1(d1 )
             , _d2(d2 )
{
     cout<<"Data<T1&, T2&>" <<endl;
}

注:模板的全特化和偏特化都是在已经定义的模板基础之上的,不能单独存在。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值