3. 资源管理

29 阅读2分钟

资源,就是一旦使用了他,将来必须归还给系统,如内存、互斥锁、文件描述器以及socket等

小结

  1. 本章虽然是资源管理,但其实就是讲解RAII对象的创建以及使用,注意这些条款,就能较好的预防资源泄漏
  2. 对象创建:需完成构造、析构、copy行为以及重载*->以及需要提供原始资源的访问
  3. 对象使用:在一条语句中完成RAII对象的初始化

条款 13:以对象管理资源

  1. RAII,资源获得即初始化(用获得资源来初始化对象)
  2. 在析构函数中释放资源,不能抛出错误
  3. unique_ptr、shared_ptr、weak_ptr

条款 14:在资源管理类中小心 coping 行为

  1. 禁用复制
  2. 底层资源引用计数(shared_ptr),注意循环引用
  3. 转移资源
  4. 深拷贝,即将资源也拷贝一份

条款 15:在资源管理类中提供对原始资源的访问

  1. 一些api往往都是需要传入原始指针的
  2. 可提供get()返回底层指针,推荐,减少风险
  3. 也可以重载类型转换,能够隐式转换,但是一般不推荐,增加了风险

条款 16:成对使用 new 和 delete时要采取相同形式

  1. new和delete、new T[]delete []
  2. 对于typedef或using,尽量不要将数组定义别名,因为可能会调用delete而不是delete[]

条款 17:以独立语句将 newed 对象置入智能指针

  1. ;划分语句,翻译之后可能会被重排
  2. 创建智能指针语句,翻译为有序两步:先new出资源,再用资源去构造RAII对象
  3. 如果语句既有智能指针的初始化,又有其他操作,重排之后,可能为new出资源然后去执行其他操作,再用资源去构造RAII对象,但是执行其他操作可能出错,导致资源没有放入RAII对象,进而内存泄露
//如果priority()调用抛出异常,已分配的Widget对象可能将无法被shared_ptr管理,导致内存泄漏
//processWidget(std::shared_ptr<Widget>(new Widget), priority());


std::shared_ptr<Widget> pw(new Widget); // 独立语句完成资源获取和RAII封装 
processWidget(pw, priority()); // 安全调用