unique_ptr f()
{
unique_ptr p(new X);
return p;
}
这里返回p的话,会产生临时对象吗,会调用拷贝构造吗,可是unique_ptr是不允许调用拷贝构造的啊,为什么可以这么写?
请各位大大指教
unique_ptr f()
{
unique_ptr p(new X);
return p;
}
这里返回p的话,会产生临时对象吗,会调用拷贝构造吗,可是unique_ptr是不允许调用拷贝构造的啊,为什么可以这么写?
请各位大大指教
3 回答2k 阅读✓ 已解决
2 回答3.9k 阅读✓ 已解决
2 回答3.2k 阅读✓ 已解决
1 回答3.2k 阅读✓ 已解决
1 回答2.7k 阅读✓ 已解决
3 回答3.4k 阅读
1 回答1.6k 阅读✓ 已解决
返回值优化
如果没有这个优化,这段代码就是错的,比如这样就没问题:
有的编译器,比如GCC/Clang,可以用
-fno-elide-constructors
禁掉 “某些” NRVO,但不包括你写的这种(过于简单的)代码;MSVC不开优化选项也可以禁掉 “某些” NRVO,但也不包括这种情况。如果你坚持要禁掉NRVO,可以这么干:
你会发现这样就编译不过了,因为在这段代码中,你给local的
unique_ptr
创建了一个alias,这样编译器就不能做这个优化,因为优化前后这个alias指向的对象是不一样的。pp
当然是个悬空的无效指针,但只要你不用它也不会出错,反正你只是要禁掉NRVO对不。那么如果一个函数真要返回一个non-copyable object怎么办呢?
注意,NRVO的“N”指的是这个优化只针对Named return value,也就是说这种优化和没名字的临时变量无关。
由于匿名临时变量都是rvalue,所以在构造真正的返回结果对象时使用的是move-constructor而不是copy constructor,而
unique_ptr
当然是move-constructible,也就是说,make_unique只需要这么写:这样就完全没问题了,无论有没有NRVO,反正它也不用。