Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/124.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 我应该使用智能指针吗?_C++_Pointers_C++11_Smart Pointers - Fatal编程技术网

C++ 我应该使用智能指针吗?

C++ 我应该使用智能指针吗?,c++,pointers,c++11,smart-pointers,C++,Pointers,C++11,Smart Pointers,我的课程如下: class node { public: node* parent; std::list<node*> children; }; 类节点 { 公众: 节点*父节点; 性病:列出儿童; }; 我应该使用智能指针而不是原始指针吗?为什么?如果是,什么类型的智能指针?使用智能指针总是一个好主意,但要注意引用循环 class node { public: std::weak_ptr<node> parent; std:

我的课程如下:

class node
{
public:

     node* parent;
     std::list<node*> children;
};
类节点
{
公众:
节点*父节点;
性病:列出儿童;
};

我应该使用智能指针而不是原始指针吗?为什么?如果是,什么类型的智能指针?

使用智能指针总是一个好主意,但要注意引用循环

class node
{
public:
     std::weak_ptr<node> parent;
     std::list< std::shared_ptr<node> > children;
};
类节点
{
公众:
std::弱ptr父代;
std::list儿童;
};

这就是为什么首先存在
弱\u ptr
。请注意,它们不太聪明,无法检测循环,您必须手动执行此操作,并使用
weak\u ptr
s来断开循环。

无论您在何处拥有资源(内存、文件等),请始终使用智能指针。手动拥有它们极易出错,并且违反了许多良好实践,例如

使用哪一种取决于您需要什么样的所有权语义
unique_ptr
最适合单一所有权和
shared_ptr
共享所有权

由于孩子们不拥有他们的父母,一个原始的父母指针是好的。但是,如果父母拥有自己的孩子,
unique\u ptr
在这里效果最好


还值得注意的是,究竟是什么,指针的链接列表?这毫无意义。为什么不提供一个值的链接列表呢?

绝对不是。通常的智能指针不适用于类似于图形的对象 结构,并应避免。在这种情况下,您有一棵树 处理来自的所有删除(和分配)没有问题
树对象本身

父指针不需要是非原始指针。@JamesKanze:可能,但不太可能,而且这里也不需要共享所有权,所以唯一所有权和原始指针是最简单的设计。@JamesKanze:不可能太晚捕获它。简单的
独特的_ptrx(新的T(…)
场景非常防弹。即使对于函数参数,也有通常的求值顺序欢闹,并且标准被善意地省略了
make_unique
(被接受为缺陷),但是您可以编写自己的,即使在这种情况下也保证正确。至于太早,除非程序员将其删除,否则不会发布
unique_ptr
。这在完全相同的时间发生,简单地从列表中删除指针,然后删除它。至于指针混淆,没有人不能区分<代码> SyddYPPTR <代码>,<代码> UnQuyPPTR < /C> >和 T*< /Cord>应该真正地编码生产C++。更不用说编译器可以方便地保护您免受这些指针的几乎所有使用错误的影响,而不是说原始指针。@JamesKanze:更复杂?对于
shared\u ptr
,它是一个非常简单的插入,当然比原始指针版本简单得多,对于
unique\u ptr
,它是一个简单的
std::move
。这里没有明显的复杂性。至于在把它移到树上后填充它,那么。。。只需在插入时给出一个非所有者引用。这正是标准容器(如
std::map
)的行为,它们的功能很好。
std::unique_ptr
可以很好地处理严格的层次图,任何DAG都可以很好地处理
std::shared_ptr
。由于问题中的结构是一个严格的层次结构,没有理由相信任何一个标准智能指针都不会完全正确。@DeadMG只要稍加努力,您就可以管理任何事情。在这种情况下,使用
unique_ptr
shared_ptr
比只处理containing
类中的所有内存管理需要付出更大的努力,而且更容易出错。@JamesKanze:我不知道您想做什么,但上次我检查时,让
std::list
为您解构它包含的值类型是免费的。@JamesKanze:您可能只需要三种类型的指针(定期)。何时使用哪一个的决定无关紧要,与何时使用
delete
的决定相同。唯一的区别是智能指针可以更可靠地实现该决策。如果你不知道什么时候删除一个对象,你会遇到比现在使用的类型更大的问题。如果您这样做了,那么您已经知道使用什么智能指针了。@JamesKanze:“对象Y负责销毁对象Z,因为“destruct”的一般定义是一个相当普遍的问题。哦,为了防止你好奇,我实际上没有否决你的答案。@JamesKanze:比如说,资源。。。子节点的内存?这种结构的基于
独特的\u ptr
的版本不可能比基于原始指针的版本可靠性更低或更复杂。事实上,
unique\u ptr
实际上是可靠和简单的定义。也许您应该详细说明为什么您认为智能指针版本会比原始指针版本更糟糕。@JamesKanze:没问题。首先,作为实现者,您不再需要手动删除节点。这保证了您不能双重删除它们,或者忘记删除它们,并且还保证了异常安全。如果你删除了所有可能会删除的代码,你就会得到它。因此,它减少了代码大小并保证了安全性。这听起来像是我能想象到的每一个方面的胜利。至于不同的指针类型,那么,在C++中,使用不同的类型来执行不同的作业。这是生活中必不可少的事实。语法清楚地表明了什么是什么。@JamesKanze:
unique\u ptr
引入的悬空指针不比
delete
引入的指针多。而
shared_ptr
仅在存在引用周期时引入内存泄漏-所有好的设计很少有,甚至非常糟糕的设计也很少有-并且没有比
delete
@JamesKanze
更多的悬空指针使用unique_ptr几乎保证了悬空指针
-我很难看到