有时候,我真的很确定我希望具有指针的循环依赖性,循环中的每个对象都应该能够使用他的指针(所以不可能是weak_ptr)。
我的问题是:这是否意味着我的设计很糟糕?
如果我想实现图形呢?我能用智能指针吗?在图中有圈,但是对于weak_ptr,我不能使用"->“。我能做什么?
我阅读了一些关于StackOverflow的文章、参考资料和主题,但看起来我仍然没有得到智能指针。真的,为什么weak_ptr不存在带有"->“的变体呢?
发布于 2014-05-01 13:48:22
从概念方面来处理这个问题,而不是从实现方面着手。智能指针代表所有权。并且,智能指针的存在并不会使原始指针作为不拥有的观察者的角色失效。
每个对象是否都有一个明确的所有者(例如,图拥有它的所有顶点和边)?如果是这样,请使用std::unique_ptr保存图中的顶点和边,并使用顶点和边内的原始指针相互引用。
是否适用共享所有权(例如,只要至少有一条边与之相连,就会存在顶点)?如果是这样的话,请使用std::shared_ptr来表示该所有权,同样使用非拥有观察者的原始指针。如果您需要相互拥有(即所有权周期),其中“一个顶点只存在于一个边引用它,而一个边只在一个顶点引用它时才存在”,那么1.双重检查这样的设计是否正确和可维护,如果是的话,在循环中的某个地方使用std::weak_ptr来打破所有权循环。您可以始终lock()一个weak_ptr来获得一个shared_ptr。
对于您的特定图形场景,我相信“所有东西都属于图”将是最符合逻辑的所有权方案;但这取决于任务的特殊性。
发布于 2014-05-01 13:38:37
您可以在循环的某个地方使用weak_ptr;您只需要将weak_ptrs提升到shared_ptrs,然后才能取消对它们的引用。您可以通过调用weak_ptr::lock()或简单地将weak_ptr传递给shared_ptr的构造函数(但要小心;如果weak_ptr指向的对象已被销毁,这将引发bad_weak_ptr异常)。
如果您真的不能这样做(例如,如果周期中涉及的所有对象都是相同类型的(可能是图示例中的情况),则另一个选项是在链中的某个位置放置一个release函数,该函数会导致该对象将其所有shared_ptr设置为null。
发布于 2014-05-02 22:10:56
这是否意味着我的设计很糟糕?
是的,但这是个起点。
让我们考虑一些可用的智能指针。
unique_ptr --存在一个单独的所有者,负责处理对象。
shared_ptr --存在许多(或潜在的)所有者,最后一个所有者必须处理该对象。
weak_ptr -许多所有者可能存在,但这不是其中之一,弱指针可能会激活指向的对象,如果指向的对象被释放,弱指针将为空(即锁方法将返回一个空shared_ptr)。
observer_ptr(n3840)- -还没有成为标准的一部分,所以如果需要的话,可以使用C样式指针(T*)。这些工作非常类似于一个weak_ptr,但程序员的责任是确保所有观察者在被指向的对象被释放后不会被取消引用。
一种解决方案是将设计分割成一个对象,该对象将拥有所有的部分和部分(循环节点)。拥有对象可以使用shared_ptr或unique_ptr自动管理节点的生存期。节点本身可以使用weak_ptr、observer_ptr或引用(Node&)相互引用。
https://stackoverflow.com/questions/23408810
复制相似问题