Effective C++ Item 13-以对象管理资源

Item 13-以对象管理资源(Use objects to manage resources


半边想法:把资源放进对象内,我们便可依赖C++的"析构函数自动调用机制"确保资源被释放。

许多资源被动态分配与heap内而后被用于单一区域或函数内。它们应该在控制流离开那个区域或函数时被释放。标准程序库提供的auto_ptr正是针对这种形势而设计的特质产品。auto_ptr是个"类指针(pointer-like)对象"也就是所谓"智能指针",其析构函数自动对其所指对象调用detele。

Ex:

class Investment{...};            //"投资类型"继承体系中的root class
Investment* createInvestment();   //返回指针,指向Investment继承体系内的动态分配对象。调用者有责任删除它。
void f()
{
    std::auto_ptr<Investment> pInv(createInvestment());
    ...
}                                 //经由auto_ptr的析构函数自动删除pInv


两个关键想法:

1、获得资源后立刻放进管理对象内(managing object)内。

f()中,createInvestment返回的资源被当做其管理者auto_ptr的初值。实际上"以对象管理资源"的观念常被称为"资源取得时机便是初始化时机"(Resource Acquisition Is Initialization; RAII),因为我们几乎总是在获得的资源被拿来赋值(而非初始化)某个管理对象,但不论哪一种做法,每一笔资源都在获得的同时立刻被放进管理对象中。

2、管理对象(managing object)运用析构函数确保资源被释放。


由于auto_ptr被销毁时会自动删除它所指之物,所以一定要注意别让多个auto_ptr同时指向同一个对象。不然对象就会删除一次以上。

所以auto_ptr有一个不寻常的性质:若通过copy构造函数或copy assignment操作符复制它们,它们会变成NULL,而复制所得的指针将取得资源的唯一拥有权。

所以,auto_ptr并不是最佳方案。
替代方案"引用计数型智慧指针"(reference-counting smart pointer; RCSP)。RCSP也是个智能指针,持续追踪共有多少对象指向某笔资源,并在无人指向它们时自动删除该资源。

Ex:

void f()
{
    ...
    std::trl::shared_ptr<Investment>
    pInv1(createInvestment());   //pInv指向createInvestment返回物理=
    std::trl::shared_ptr<Investment>
    pInv2(pInv1);                //pInv1和pInv2指向同一个对象
    pInv1=pInv2;
    ...
}                                //pInv1和pInv2都被销毁

请记住:

为防止资源泄漏,请使用RAII对象,它们在构造函数中获得资源并在析构函数中释放资源。

两个常被使用的RAII classes分别是trl::shared_ptr和auto_ptr。前者是较佳选择,因为其copy行为比较直观。若选择auto_ptr,复制动作会使它(被复制物)指向NULL。

你可能感兴趣的:(C++,effective)