我知道有weak_ptr
打破了这个循环,但这是一个修复,发现问题后。是否有可用于检测或避免循环引用的模式或工具?如何检测或避免使用std :: shared_ptr的循环引用?
回答
我强烈地回应sellibitze所说的话,并重新考虑设计。如果你真正拥有的是单向所有权,而只是在相反的方向观察,可以考虑weak_ptr。这使您可以检查一个对象是否处于活动状态,但不会仅仅因为您有一个指向它的对象而使对象保持活动状态。
明显的答案是不要使用shared_ptr
对象,其中 本身可能包含shared_ptr
。 shared_ptr
是有点特别的,应该谨慎使用 。
您可以通过设计避免这种情况。正如Stephan T. Lavavej在GoingNative2012会议上指出的那样(您可以在线查看视频),“所有权”是一个有向非循环图,即DAG。 DAG中没有周期。如果你的所有权图不是DAG,你的设计是......可疑的,因为拥有B和B的拥有A是没有意义的。但shared_ptr是一个“共享所有者指针”。持有这种指针的对象或作用域拥有指针。尝试从所有权图的角度思考。
shared_ptr不是每个案例的正确工具。它不应该让你编写代码,就像你在Java中一样,你不必考虑所有权(很多)。它应该提供自动和确定性的清理。如果你需要一个“非拥有”指针,weak_ptr或者一个原始指针是合适的。只要确保一个原始指针指向的对象保持足够长的时间。
Java仍然没有确定性的对象破坏。 Java确实使用(){}构造支持像C#这样的构造,但这远离C++对象销毁提供的确定性。 – Unknown1987 2012-02-23 23:29:40
我没有声称Java确实有对象破坏。 – sellibitze 2012-02-24 11:12:36
你可以实现一个,就像创建this
指针(例如通过宏)的smart_ptr
上的包装一样。然后建立带有从存储的this
到shared_ptr
包含的对象的边的有向图并检测任何周期,例如,通过拓扑排序。
我会推荐这只适用于密集的shared_ptr
使用和无法控制所有设计方面的大型代码库。对于其他情况只需使用@sellibitze建议。
- 1. 使用std :: shared_ptr检测循环引用
- 2. 使用@XmlIDREF避免JAXB循环引用
- 3. 如何避免使用Spark循环?
- 4. 如何避免使用JPA进行循环引用注释?
- 5. 避免循环引用服务和DI
- 6. 在Swing GUI中避免循环引用
- 7. 试图避免循环引用
- 8. 如何检测和避免PHP中的死循环
- 9. C#如何检测循环引用?
- 10. 检测循环引用
- 11. 如何避免infinte循环
- 12. 如何避免循环
- 13. 在使用之前,我应该检查boost :: shared_ptr或std :: shared_ptr吗?
- 14. 如何避免项目之间的循环引用?
- 15. 如何使用weak_ptr破坏shared_ptr循环引用
- 16. excel单元格更新时如何避免循环引用
- 17. 如何避免游戏渲染组件循环引用?
- 18. 如何避免循环引用,而序列化实体框架
- 19. 如何在Backbone.js中避免使用循环引用的堆栈溢出?
- 20. 避免使用嵌套for循环
- 21. 我如何使用box2d使用std :: shared_ptr?
- 22. 避免while循环
- 23. 避免for循环
- 24. 循环引用检测的LINQ
- 25. 检测对象中的循环引用
- 26. 检测RxUI中的循环引用
- 27. 在lxml中测试元素时避免循环使用
- 28. 检测或避免在编译时
- 29. 避免在索引页循环
- 30. 避免Numpy索引For循环
我没有设计来重新思考。我想知道如何设计,所以我没有这个问题。 – 2012-02-23 19:23:16
没有进一步的背景,不可能推荐如何构建关系。我会考虑谁拥有谁的问题。如果你最终的模型是一个意大利面杂乱的指针太难以保持所有权明确定义,显然这不是一个设计良好的模块。将问题分解为更小的块,以便将其封装。通过这种方式,您可以构建足够简单的所有权层次结构。 – Unknown1987 2012-02-23 23:25:25