c – weak_ptr VS shared_ptr在图形节点父列表中
我有一个由Graph和Node类实现的有向无环图.每个节点都有一个指向childern的指针列表和一个指向父节点的指针列表.我最近添加了父母,因为一些算法需要快速访问父列表,而且图形很小,每个节点只有很少的连接,所以没有内存问题.
子列表使用std :: shared_ptr,以便节点保存在内存中至少与父节点一样长.但是我不想让一个节点拥有它的父母,所以我使用weak_ptr作为父母的指针. 但是,算法存在问题.一个算法必须从weak_ptr创建一个新的shared_ptr,所以我不能直接使用operator ==,并且使用标准函数(如std :: find())需要编写一个名为my_weak_ptr.lock()的lambda函数,然后比较它到一些shared_ptr. 如果我切换到shared_ptr,代替节点删除的代码中的任何小错误都可能导致内存泄漏.或者如果我有一个指向已经删除的节点的指针,代码将能够访问不应该存在的节点,因此发现一些错误可能会变得更加困难.但是使用shared_ptr与weak_ptr一样安全,因为不取消引用/删除/ etc.当不应该(因为它比原始的C指针好)和std :: find()可以直接使用,因为shared_ptr可以被取消引用,不像weak_ptr. 这里是否有“更好”的设计,或者这是具体情况的一个问题,这取决于例如如果我执行了weak_ptr :: lock()的额外操作,还是冒着难以发现的错误的风险呢? 解决方法
正如你所说,在双向使用shared_ptr将创建创建mem泄漏并且很难找到并破坏的圈子 – 您将丢失(几乎)shared_ptr提供的所有好处.所以weak_ptr应该是.
你说你的算法必须锁定weak_ptr – 我希望有所不同.这些算法必须从节点获取一个父类shared_ptr.锁定父级的weak_ptr是节点的任务,并将结果返回给父节点或NULL. 这是一个实现细节,节点将他们的父节点存储为shared_ptr或weak_ptr.仅通过向任何客户端提供shared_ptrs来封装该细节. class Node { /* ... */ std::weak_ptr<Node> parent; public: std::shared_ptr<Node> getParent() { return parent.lock(); } }; 编辑: EDIT2: template <class WPIterator> struct LockTheWeakIterator { //static_assert that WPiterator's value_type is some weak_ptr //typedef all those iterator typedefs typedef typename WPIterator::value_type::element_type element_type; shared_ptr<element_type> operator*() { return iter->lock(); } //provide all the other operators - boost.operators might help with that... WPIterator iter; }; template <class IT> LockTheWeakIterator<It> lockTheWeak(It iter); //somewhere... auto theParentIter = std::find_if(lockTheWeak(parents.begin()),lockTheWeak(parents.end()),whatIAmLookingFor); (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |