类模板就是一系列相关类的模型或样板,这些类的成员组成相同,成员函数的源代码形式相同,所不同的只是所针对的类型(成员的类型以及成员函数的参数和返回值的类型)不同。对于类模板,数据类型本身成为了它的参数,因而是一种参数化类型的类,是类的生成器。类模板中声明的类称为模板类。
示 例:
#include<iostream>
#include<iomanip>
#include<cstdlib> //使用库函数exit()
using namespace std;
template<typename TYPE> //类模板声明以此开头
class array
{
int _size;
TYPE * data; //区分不同类模板实例的有关类型应使用虚拟类型
public:
array(int n);
~array(){delete []data;}
TYPE &operator [](int i);
int size()const{return _size;}
};
template<typename TYPE>
array<TYPE>::array(int n)
{
if(n<1){
cout<<"Error dimension description";
exit(1);
}
_size=n;
data=new TYPE[_size];
}
template<typename TYPE>
TYPE &array<TYPE>::operator [](int i){
if(i<1||i>_size){
cout<<endl<<"Subscript out of range";
delete []data;
exit(2);
}
return data[i-1];
}
int main(){
array<int> a(5);
int i;
for(i=1;i<=a.size();i++) a[i]=i;
for(i=1;i<=a.size();i++) cout<<setw(5)<<a[i];
cout<<endl<<endl;
array<double> b(5);
for(i=1;i<=b.size();i++) b[i]=i+i/10.0;
cout.precision(2);
for(i=1;i<=b.size();i++) cout<<setw(5)<<b[i]<<' ';
cout<<endl<<endl;
system("pause");
return 0;
}
程序运行结果:
从上例可以看出类模板的定义格式,其中要注意三个环节的语法格式。
(1)声明一个类模板的格式:
template <<模板形参表>> <类声明>
<模板形参表>由一个或多个模板形参组成;与一般的类声明的不同之处在于,这里的<类声明>要用<模板形参表>中声明的虚拟类型参数来修饰它的某些成员,使模板类独立于任何具体的数据类型。
(2)在模板外定义的成员函数是一个函数模板,其定义格式:
template<模板形参表>
<返回类型> <类名><<模板形参表>>::<函数名>(<函数形参表>)<函数体>
注:类模板的成员函数都是模板函数,因此在模板外定义的成员函数的格式与定义普通模板函数十分相似。
(3)用类模板定义对象的格式:
<类名><<模板形参表>> <对象名>; 或 <类名><<模板形参表>> <对象名>(<构造函数实参表>);
在定义对象的过程中,编译系统会自动地根据需要生成相应的类定义,这种依据类模板生成类定义的过程称为类模板的实例化。类模板实例化所生成的每一个类定义就是相应类模板的一个实例。
在用类模板定义对象时,可以为类模板的参数设置默认值。具体地说,在定义类模板时,可以为模板形参表声明的最后若干个参数设置默认值;而这些有默认值的参数中,最后的若干个对应实参可以在定义对象时省略。