1 基本概念
模板是泛型编程的基础,泛型编程即以一种独立于任何特定类型的方式编写代码。
泛型编程:编写与类型无关的通用代码,是代码复用的一种手段。模板是泛型编程的基础。
模板是创建泛型类或函数的蓝图或公式。库容器,比如迭代器和算法,都是泛型编程的例子,它们都使用了模板的概念。
每个容器都有一个单一的定义,比如 向量,我们可以定义许多不同类型的向量,比如 :
vector <int>
vector <string>
2 函数模板介绍
函数模板代表了一个函数家族,该函数模板与类型无关,在使用时被参数化,根据实参类型产生函数的特定类型版本。
template <typename T1,typename T2,....>
返回值类型 函数名(参数列表)
{
}
template<typename T>
void MySwap(T& a, T& b)
{
T tmp = a;
a = b;
b = tmp;
}
函数模板是一个蓝图,它本身并不是函数,是编译器用使用方式产生特定具体类型函数的模具。所以其实模板就是将本来应该我们做的重复的事情交给了编译器。在编译器编译阶段,对于模板函数的使用,编译器需要根据传入的实参类型来推演生成对应类型的函数以供调用。 用不同类型的参数使用函数模板时,称为函数模板的实例化。模板参数实例化分为:隐式实例化和显式实例化。隐式实例化不必多说,就是上文提到的编译器进行实参类型推演出对应函数。
下面介绍显示实例化,即在函数名后的<>中指定模板参数的实际类型。
template<typename T>
T myAdd(T a, T b)
{
return a + b;
}
int main()
{
myAdd(1, 3);
myAdd<double>(1.3, 4.3);
return 0;
}
如果类型不匹配,编译器会尝试进行隐式类型转换,如果无法转换成功编译器将会报错。注意:模板函数不允许自动类型转换,但普通函数可以进行自动类型转换
3 类模板介绍
template<class T1, class T2, ..., class Tn>
class 类模板名
{
};
template<class T>
class MyVerter
{
public:
MyVerter(size_t size = 0,size_t capacity = 10)
:_pData(new T[capacity])
,_size(0)
,_capacity(capacity)
{}
~MyVerter<T>()
{
if (_pData)
delete[] _pData;
_size = _capacity = 0;
}
size_t Size()
{
return _size;
}
private:
T* _pData;
size_t _size;
size_t _capacity;
};
类模板实例化与函数模板实例化不同,类模板实例化需要在类模板名字后跟<>,然后将实例化的类型放在<>中即可,类模板名字不是真正的类,而实例化的结果才是真正的类。
int main()
{
MyVerter<int> v1;
MyVerter<char> v2;
return 0;
}
|