unique_ptr :: release()是否会调用析构函数?

Zeu*_*kis 54 c++ unique-ptr

这段代码是否正确?

auto v =  make_unique<int>(12);
v.release();     // is this possible?
Run Code Online (Sandbox Code Playgroud)

它等同于delete原始指针吗?

Mik*_*our 120

不,代码导致内存泄漏.release用于释放托管对象的所有权而不删除它:

auto v = make_unique<int>(12);  // manages the object
int * raw = v.release();        // pointer to no-longer-managed object
delete raw;                     // needs manual deletion
Run Code Online (Sandbox Code Playgroud)

除非你有充分的理由在没有安全网的情况下处理原始内存,否则不要这样做.

要删除对象,请使用reset.

auto v = make_unique<int>(12);  // manages the object
v.reset();                      // delete the object, leaving v empty
Run Code Online (Sandbox Code Playgroud)

  • @Cyber​​:这是一个品味问题.我不认为指针限定符是"附加"到类型或变量,所以我不会将它附加到任何一个. (11认同)
  • 如果觉得很难过,他们决定使用这些函数名称.像'detach`这样的东西比'释放'更具误导性. (9认同)
  • 作为一个完全偏离主题的切线,我看到有人写`int*raw`和`int*raw`,但这是我第一次见到`int*raw` (5认同)
  • 我不同意@nenchev。我认为 nullptr 的赋值更清晰。除了删除指向的对象(它是 unique_ptr)之外,它实际上无能为力,因为它显然用 nullptr 替换了当前值。对于reset(),您必须阅读文档才能确定该函数的确切作用。 (4认同)

Joh*_*ell 23

这段代码是否正确?

不可以.std::unique_ptr<>::reset()用于删除内部原始指针:

auto v =  std::make_unique<int>(12);
v.reset(); // deletes the raw pointer
Run Code Online (Sandbox Code Playgroud)

完成后,std::unique_ptr<>::get()将返回nullptr(除非您提供了非nullptr参数std::unique_ptr<>::reset()).


JBL*_*JBL 17

这段代码是否正确?

它不会,也会泄漏.

release()让调用代码收回所有内存的所有权,unique_ptr直到调用它为止.如果你没有指定返回的指针release(),你就会发生泄漏.

显式删除a unique_ptr将是reset().但请记住,unique_ptr那样你就不必直接管理他们所拥有的记忆.也就是说,你应该知道,unique_ptr一旦它超出范围,它将安全地删除它的底层原始指针.

因此,您应该有充分的理由在自动内存管理对象上执行手动内存管理.


Cor*_*mer 11

release 将您的原始指针泄漏,因为您没有将其分配给任何东西.

它意味着用于类似的东西

int* x = v.release();
Run Code Online (Sandbox Code Playgroud)

这意味着v不再管理该指针的生命周期,它将原始指针所有权委托给x.如果你release没有分配任何东西,你会泄漏原始指针.


Mic*_*ser 5

对于任意类型来说可能有点棘手:

  unique_ptr<Foo> v = get_me_some_foo();  // manages the object
  Foo * raw = v.release();        // pointer to no-longer-managed object
  delete raw;
Run Code Online (Sandbox Code Playgroud)

几乎是正确的。

  unique_ptr<Foo> v = get_me_some_foo();  // manages the object
  Foo * ptr = v.release();        // pointer to no-longer-managed object
  v.get_deleter() ( ptr );
Run Code Online (Sandbox Code Playgroud)

这个在所有情况下都是正确的;Foo 类型上可能定义了一个自定义删除器,但使用 unique_ptr 对象返回的删除器适用于所有情况。