非类型模版参数模版的特化分离编译

Posted 燕麦冲冲冲

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了非类型模版参数模版的特化分离编译相关的知识,希望对你有一定的参考价值。

模版进阶

非类型模版参数

泛型编程
函数模版+类模版

实现静态栈
缺点类中的数组大小是固定值。可以通过定义数组大小的宏变量来快速修改大小。但比如第一个栈要100空间,第二个栈要200,那么第一个栈就会造成空间的浪费。

C++提供了解决策略:提供非类型模版参数
原来的template 中的T为类型模版参数。

template <class T, size_t N = 10>
class stack

    int _a[N];
    int top;
;

stack<int, 100> st1;
stack<int, 10000> st2;

上述示例中,N为一个常量。
模版参数都可以给缺省值,模版参数给缺省值和函数参数给缺省值是完全类似的。可以全缺省或半缺省。
整型才可以做模版参数。

为什么不建议任何人使用静态容器array(一个类似于上面示例中的类)?
因为是在栈上使用的,而栈上空间十分有限,非常不建议使用大空间的。

arrar和forward_list非常鸡肋,所以被吐槽。
C++的缺点之一,后期C++11等等标准增加了不少鸡肋的语法,让语言变得臃肿,学习成本增加。一些刚需的东西姗姗来迟,甚至还没有来(网络库)。

模版的特化

针对某些类型进行特殊化处理

template<class T>
void Swap(T& a, T& b)

    T tmp = a;
    a = b;
    b = tmp;

//函数模版的特化
template<>
void Swap<vector<int>>(vector<int>& v1, vector<int>& v2)

    v1.swap(v2);

不推荐使用,还不如直接根据模版匹配原则进行特殊化处理。

常用的是类模版的特化

template<class T1, class T2>
class Data

public:
    Data()
    
        cout << "<T1, T2>" << endl;
    
;
//类模版的特化
template<>
class Data<double, double>

public:
    Data()
    
        cout << "<double, double>" << endl;
    
;
//偏特化
template<class T>
class Data<T, char>

public:
    Data()
    
        cout << "<T, char>" << endl;
    
;
//偏特化:不一定是特化部分参数,而是对模版参数类型的进一步限制
template<class T1, class T2>
class Data<T1&, T2&>

public:
    Data()
    
        cout << "<T1&, T2&>" << endl;
    
;

template<class T1, class T2>
class Data<T1*, T2*>

public:
    Data()
    
        cout << "<T1*, T2*>" << endl;
    
;

int main()

    Data<double, double> d1;
    Data<int, int> d2;
    Data<int, char> d3;
    Data<int&, char&> d4;
    Data<int*, char*> d5;
    return 0;

分离编译

顾名思义,就是main.c与函数实现.c与头文件一起编译。
但是模版不支持分离编译,所以只能有main.c与.h文件


解决方案就是将模版定义直接放在头文件中。

以上是关于非类型模版参数模版的特化分离编译的主要内容,如果未能解决你的问题,请参考以下文章

模版的完全特化与偏特化

C++模板进阶操作 —— 非类型模板参数模板的特化以及模板的分离编译

C++初阶:模板进阶非类型模板参数 | 模板的特化 | 模板分离编译

C++初阶:模板进阶非类型模板参数 | 模板的特化 | 模板分离编译

C++初阶:模板进阶非类型模板参数 | 模板的特化 | 模板分离编译

C++模板详解:泛型编程模板原理非类型模板参数模板特化分离编译