问题标签 [smart-pointers]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
12 回答
10913 浏览

c++ - 查找由智能指针引起的内存泄漏

有人知道发现智能指针引起的内存泄漏的“技术”吗?我目前正在开发一个用C++编写的大型项目,该项目大量使用带有引用计数的智能指针。显然,我们有一些由智能指针引起的内存泄漏,它们仍然在代码中的某处被引用,因此它们的内存不会被释放。很难找到带有“不必要”引用的代码行,这会导致相应的对象不被释放(尽管它不再使用)。

我在网上找到了一些建议,建议收集引用计数器的递增/递减操作的调用堆栈。这给了我一个很好的提示,哪段代码导致引用计数器增加或减少。

但我需要的是某种算法,将相应的“增加/减少调用堆栈”组合在一起。删除这对调用堆栈后,我希望(至少)剩下一个“增加调用堆栈”,它向我展示了带有“不必要”引用的代码段,导致相应的对象未被释放。现在修复泄漏没什么大不了的!

但是有人对进行分组的“算法”有想法吗?

开发在Windows XP下进行。

(我希望有人理解,我试图解释的......)

编辑:我说的是循环引用引起的泄漏。

0 投票
11 回答
59065 浏览

c++ - 智能指针:谁拥有对象?

C++ 是关于内存所有权的——也就是所有权语义

一块动态分配的内存的所有者有责任释放该内存。所以问题真的变成了谁拥有记忆。

在 C++ 中,所有权由包装在内部的原始指针的类型记录,因此在一个好的(IMO)C++ 程序中,很少(很少,不是从不)看到传递的原始指针(因为原始指针没有推断的所有权,因此我们可以不知道谁拥有内存,因此如果不仔细阅读文档,您就无法知道谁负责所有权)。

相反,很少看到原始指针存储在一个类中,每个原始指针都存储在其自己的智能指针包装器中。(注意:如果您不拥有一个对象,则不应存储它,因为您不知道它何时会超出范围并被销毁。)

所以问题:

  • 人们遇到了什么类型的所有权语义?
  • 使用哪些标准类来实现这些语义?
  • 你觉得它们在什么情况下有用?

让我们为每个答案保留一种语义所有权,以便可以单独对它们进行上下投票。

概括:

从概念上讲,智能指针很简单,简单的实现也很容易。我见过许多尝试的实现,但它们总是以某种方式被破坏,这对于随意使用和示例来说并不明显。因此,我建议始终使用库中经过良好测试的智能指针,而不是自己滚动。std::auto_ptr或者 Boost 智能指针之一似乎可以满足我的所有需求。

std::auto_ptr<T>

单身人士拥有该物品。允许转让所有权。

用法:这允许您定义显示所有权显式转移的接口。

boost::scoped_ptr<T>

单身人士拥有该物品。不允许转让所有权。

用法:用于显示明确的所有权。对象将被析构函数或显式重置时销毁。

boost::shared_ptr<T>( std::tr1::shared_ptr<T>)

多重所有权。这是一个简单的引用计数指针。当引用计数达到零时,对象被销毁。

用法:当一个对象可以有多个生命周期无法在编译时确定时。

boost::weak_ptr<T>

shared_ptr<T>在可能发生指针循环的情况下使用 with 。

用法:用于在只有循环维护共享引用计数时停止循环保留对象。

0 投票
14 回答
660513 浏览

c++ - 什么是智能指针,我应该什么时候使用它?

什么是智能指针,我应该什么时候使用它?

0 投票
3 回答
4169 浏览

c++ - 提升 shared_ptr 容器问题

假设我有一个多线程应用程序使用的指针容器(std::vector)。在向容器添加新指针时,代码使用临界区 (boost::mutex) 进行保护。一切都很好。代码应该能够将这些指针之一返回给线程以进行处理,但另一个单独的线程可以选择删除这些指针之一,该指针可能仍在使用中。例如:

所以thread2可以在thread1使用它时删除指针。讨厌。

因此,我想使用 Boost 共享 ptrs 的容器。IIRC 这些指针将被引用计数,因此只要我返回共享 ptrs 而不是原始指针,从容器中删除一个不会真正释放它,直到最后一次使用它超出范围。IE

在上面的例子中,如果thread1在thread2调用erase之前获得了指针,那么指向的对象是否仍然有效?当thread1完成时它实际上不会被删除?请注意,对全局向量的访问将通过临界区进行。

我认为这就是 shared_ptrs 的工作方式,但我需要确定。

0 投票
3 回答
2870 浏览

c++ - 指针和容器

我们都知道 RAW 指针需要包装在某种形式的智能指针中才能获得 Exception 安全的内存管理。但是当涉及到指针容器时,问题变得更加棘手。

std 容器坚持包含的对象是可复制的,因此这排除了 std::auto_ptr 的使用,尽管您仍然可以使用 boost::shared_ptr 等。

但也有一些 boost 容器明确设计用于安全地保存指针:
请参阅指针容器库

问题是:在什么情况下我应该更喜欢使用 ptr_containers 而不是 smart_pointers 容器?

0 投票
3 回答
7397 浏览

c++ - boost::shared_ptr 标准容器

假设我有一个类 foo,并希望使用 std::map 来存储一些 boost::shared_ptrs,例如:

如果我向地图添加了一个新的 foo_sp 但使用的键已经存在,是否会删除现有条目?例如:

原来的指针(p)被p2替换后会被释放吗?我很确定它会是,但我认为值得询问/分享。

0 投票
3 回答
6778 浏览

c++-cli - 托管 C++/CLI 类中的 auto_ptr 或 shared_ptr 等效项

在 C++/CLI 中,您可以在托管类中使用本机类型,但不允许在托管类中持有本机类的成员:在这种情况下您需要使用指针。

这是一个例子:

有人知道 C++/CLI 世界中的 shared_ptr 等价物吗?

编辑:感谢您的建议,“1800-信息”。根据您的建议,我检查了 STL.Net,但它仅适用于 Visual Studio 2008,它提供容器 + 算法,但没有智能指针。

0 投票
6 回答
13801 浏览

c++ - 为什么不应该使用对智能指针的引用?

我记得在某处读过使用对智能指针的引用会导致内存损坏。这仅仅是因为在智能指针被销毁后使用了它的引用吗?还是引用计数搞砸了?

感谢您的澄清

0 投票
7 回答
17665 浏览

c++ - 如何将协变返回类型与智能指针一起使用?

我有这样的代码:

此代码无法编译。

在视觉工作室它提出

C2555:覆盖虚函数返回类型不同且不是协变的

如果我不使用boost::shared_ptr但返回原始指针,则代码编译(我理解这是由于 C++ 中的协变返回类型)。我可以看到问题是因为不是从boost::shared_ptrof派生的。但是我想返回用于其他类,否则我必须在返回后转换返回值。 Ret1boost::shared_ptrRetInterfaceboost::shared_ptrRet1

  1. 难道我做错了什么?
  2. 如果不是,为什么这种语言是这样的——在这种情况下处理智能指针之间的转换应该是可扩展的?是否有理想的解决方法?
0 投票
5 回答
4532 浏览

c++ - 惯用 std::auto_ptr 还是只使用 shared_ptr?

现在shared_ptr在 tr1 中,您认为使用 应该发生std::auto_ptr什么?它们都有不同的用例,但auto_ptr也可以用 解决所有用例shared_ptrauto_ptr如果您想明确表示在任何给定点上只有一个类拥有所有权,您会放弃还是继续使用它?

我的看法是,使用auto_ptr可以增加代码的清晰度,正是通过增加细微差别和代码设计的指示,但另一方面,它在培训新程序员时增加了另一个微妙的问题:他们需要理解智能指针和它们如何工作的详细信息。当您在任何地方只使用一个智能指针时,您只需制定一条规则“将所有指针包装在shared_ptr”中并完成它。

你对此有何看法?