[C++]模板与泛型编程(3)

本文探讨了C++中成员模板的应用,包括作为类成员的函数模板和类模板的成员模板。通过具体示例展示了如何使用成员模板实现自定义删除器,并讨论了类模板成员模板的构造函数定义方式以及显示实例化的概念。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

成员模板

普通(非模板)类的成员模板
我们设计一个类,包含一个重载的函数调用运算符,它接受一个指针并对此指针执行delete。与默认删除器不同,我们还在删除器被执行时打印一条信息。

class DebugDelet{
public:
    DebugDelet(std::ostream &s =std::cerr):os(s){}
    //与任何函数模板一样,T的类型有编译器推断
    template <typename T>
    void operator()(T *p) const
    {os <<"deleting unique_ptr" << std::endl; delete p;}
private:
    std::ostream os;
};

double *p = new double;
DebugDelete d;  //可像delete表达式一样使用的对象
d(p);   //调用DebugDelete::operator()(double*),释放p
int* ip = new int;
//在一个临时DebugDelete对象上调用operator()(int*)
DebugDelete()(ip);

//也可以将DebugDelete用作unique_ptr的删除器。
unique_ptr<int,DebugDelete> p(new int, DebugDelete());

这里传入unique_ptr的删除器还可以用函数,
void DebugDelete2(double *d){
cout << “Deleter called\n”;
delete d;
}
unique_ptr

类模板的成员模板

以Blob为例,我们为Blob类定义一个构造函数,它接受两个迭代器,表示要拷贝的元素的范围。

template<typename T>
class Blob{
    template<typename It>
    Blob(It b, It e);
};

在类的外部定义时,必须同时提供类模板和函数模板的模板参数列表。

template<typename T>    //类模板的参数
template<typename It>
Blob<T>::Blob(It b,It e):data(std::make_shared<std::vector<T>>(b,e)){}

控制实例化

在大系统中,在多个文件中实例化相同模板的开销可能非常严重。在新标准中,我们可以通过显示实例化(explicit instantiation)来避免这种开销。

extern template declaration;    //实例化声明
template declaration;   //实例化定义

declaration是一个类或函数声明,其中所有模板参数已被替换为模板参数。例如,

//实例化声明与定义
extern template class Blob<string>;     //声明
template int compare(const int&, const int&);   //定义

extern声明就表示承诺会在程序其他位置有该实例化的一个非extern声明(定义)。

//Application.cc
//这些模板类型必须在程序的其他位置进行实例化
extern template class Blob<string>;
extern template int compare(const int&, const int&);
Blob<string> sa1,sa2;   //实例化会出现在其他位置

//Blob<int>及其接受initializer_list的构造函数将在本文件中实例化
Blob<int> a1={1,2,3};
Blob<int> a2(a1);   //拷贝构造函数在本文件中实例化
int i = compare(a1[0],a2[0]);   //实例化出现在其他位置
//templateBuild.cc
//实例化文件必须为每个在其他文件中声明为extern的类型和函数提供一个(非extern)的定义
template int compare(const int&,const int&);
templalte class Blob<string>;   //实例化模板的所有成员

实例化定义会实例化所有成员

与类模板成员函数的实例化不同(一个类模板的成员函数只有在使用到它时才进行实例化,这一特性使得即使某种类型不能完全符合模板操作的要求,我们依然能用该类型实例化类)。一个类模板的实例化定义会实例化所有成员。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值