分享免费的编程资源和教程

网站首页 > 技术教程 正文

C++核心指南(17) I.11 禁止使用指针(T*)或引用(T&)来转移所有权

goqiw 2024-10-04 22:07:20 技术教程 19 ℃ 0 评论

I.11: 永远不要使用原始指针(T*)或引用(T&)来转移所有权

原因

如果对调用者或被调用者是否拥有对象有任何疑问,就会发生泄漏或过早析构。

示例

考虑:

 X* compute(args) // 不要这样做
 {
 X* res = new X{};
 // ...
 return res;
 }

谁来删除返回的X?当compute返回一个引用时,则更难发现问题。考虑按值返回结果(如果结果很大,使用move语义):

 vector<double> compute(args) // good
 {
 vector<double> res(10000);
 // ...
 return res;
 }

可选方法: 传递所有权 使用"智能指针",如unique_ptr(独占所有权)和shared_ptr(共享所有权),然而,这并不会比返回对象本身更优雅和高效,所以只有在需要引用语义时才使用智能指针。

可选方法: 有时,由于ABI的兼容性要求和资源缺失,导致更旧代码无法修改,在这种情况下,使用指南支持库中的owner标记拥有指针:

 owner<X*> compute(args) // 现在很清楚,所有权已经转移
 {
 owner<X*> res = new X{};
 // ...
 return res;
 }

这告诉分析工具res是所有者,也就是说,它的值必须被delete或转移到另一个所有者,就像这里的return所做的那样。owner在资源句柄的实现中有也类似应用。

Note

作为原始指针(或迭代器)传递的每个对象都假定为调用者所拥有,因此它的生命周期由调用者处理。从另一个角度来看:与指针传递API相比,所有权转移API相对较少,因此默认为“无所有权转移”。

另请参阅: 参数传递、 智能指针参数的使用 和 按值返回.

实施

  • (简单) 警告delete非owner<T>的原始指针,建议使用标准库资源句柄或使用owner<T>。
  • (简单) 每条代码路径上reset或显式delete一个owner指针时,警告失败。
  • (简单) 如果new的返回值或带owner返回值的函数调用被分配给原始指针或非owner引用,则发出警告。

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表