c ++构造函数中的异常安全 [英] c++ exception safety in constructor
问题描述
下面的代码
MyClass a(new Foo(),new Bar());
如果new Foo()成功,但new Bar泄漏?
正在服用
std :: unique_ptr< Foo&
或
std :: shared_ptr< Foo>
作为参数,足以防止泄漏?
是的。
,足以防止泄漏?
不一定。这取决于你如何传递参数。例如,即使你的类构造函数看起来像这样:
MyClass :: MyClass(std :: unique_ptr< Foo& std :: unique_ptr< Bar> bar)
以下可能仍然导致泄漏:
MyClass a(std :: unique_ptr< Foo>(new Foo()),std :: unique_ptr< Bar>(new Bar这是因为编译器可以按照以下顺序对上面的表达式求值:
$ b < >
- 评估表达式
new Foo()
- 评估表达式
new Bar()
- 构建
std :: unique_ptr< Foo>
临时从1的结果。 - 从结果2构造
std :: unique_ptr< Bar>
如果2)抛出异常,您已失去了 Foo
。
但是,可以使用 std :: make_unique<>()
++ 14)或 std :: make_shared<>()
,如下所示:
<
MyClass a(std :: make_unique< Foo>(),std :: make_unique< Bar>());
现在没有泄漏可能发生,因为 std :: make_unique< ()
(和 std :: make_shared<>()
)立即将它们创建的对象关联到相应的智能指针, (动态分配和智能指针的构造)与任何其他操作交错。
What about following code
MyClass a(new Foo(), new Bar());
if "new Foo()" is successful, but "new Bar()" throws, will Foo leak?
Is taking
std::unique_ptr<Foo>
or
std::shared_ptr<Foo>
as parameters, enough to prevent the leak?
if "new Foo()" is successful, but "new Bar()" throws, does Foo will leak?
Yes.
Is taking [...] as parameters, enough to prevent the leak?
Not necessarily. It depends on how you pass the parameters. For instance, even supposed your class constructor looks like this:
MyClass::MyClass(std::unique_ptr<Foo> foo, std::unique_ptr<Bar> bar)
The following may still cause a leak:
MyClass a(std::unique_ptr<Foo>(new Foo()), std::unique_ptr<Bar>(new Bar())
That is because the compiler may is allowed to evaluate the above expressions in the following order:
- Evaluate the expression
new Foo()
- Evaluate the expression
new Bar()
- Construct the
std::unique_ptr<Foo>
temporary from the result of 1. - Construct the
std::unique_ptr<Bar>
temporary from the result of 2.
If 2) throws an exception, you've lost your Foo
.
However, it is possible to make this safe by using std::make_unique<>()
(C++14 only) or std::make_shared<>()
, like so:
MyClass a(std::make_unique<Foo>(), std::make_unique<Bar>());
Now no leak could possibly happen, because std::make_unique<>()
(and std::make_shared<>()
) immediately associate the object they create to the corresponding smart pointer, without these two operations (dynamic allocation and construction of the smart pointer) being interleaved with any other operation.
这篇关于c ++构造函数中的异常安全的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!