Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/140.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

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/wix/2.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++ 使用unique_ptr作为方法参数-优缺点_C++_Unique Ptr - Fatal编程技术网

C++ 使用unique_ptr作为方法参数-优缺点

C++ 使用unique_ptr作为方法参数-优缺点,c++,unique-ptr,C++,Unique Ptr,我注意到如果我有以下几点: #include <memory> using namespace std; class Foo { public: Foo(); }; class Wobble { public: void SetWibble( unique_ptr<Foo> foo ) { this->wibble = move( foo ); } // I like returning a ref as

我注意到如果我有以下几点:

#include <memory>
using namespace std;

class Foo
{
public:
    Foo();
};

class Wobble
{
public:
    void SetWibble( unique_ptr<Foo> foo )
    {
        this->wibble = move( foo );
    }

    // I like returning a ref as it gives control to 
    // the user of my framework over recieving a & or a copy
    Foo& GetWibble() 
    {
        return *wibble;
    }

    unique_ptr<Foo> wibble;
};

int _tmain(int argc, _TCHAR* argv[])
{
    unique_ptr<Wobble> wobble;    

    unique_ptr<Foo> foo( new Foo() ); // Look here   
    foo->something = ...;
    foo->something1 = ...;
    foo->something2 = ...;

    wobble->SetWibble( move( foo ) );

    return 0;
}
它仍然在范围内保留对该变量的引用

Q:

  • 我上面说的对吗
  • 我想知道除了我已经指出的以外,在这里使用unique_ptr和不使用unique_ptr是否还有什么好处

  • 两个示例之间的主要区别不是使用
    std::unique_ptr
    ,而是使用动态内存分配与堆栈上的分配

    通常最好在堆栈上分配对象。您将避免动态内存分配的成本和不必要的指针间接寻址(我看不出有任何理由不首先在堆栈上分配
    Wobble

    如果您只关心在您的作用域中有一个变量,也许您可以将
    Foo
    的创建提取到一个单独的函数中:

    Foo createFoo() {
        Foo foo;
        foo.something = ...;
        foo.something1 = ...;
        foo.something2 = ...;
        return foo;
    }
    
    int main() {
        Wobble wobble;
        wobble.SetWibble(createFoo());
    } 
    
    或者,如果
    Foo
    是可移动的,则可以直接移动它,而不是移动
    std::unique\u ptr

    如果这样做,您可能需要优化r值引用的
    SetWibble
    。即使移动
    foo
    没有特别的效率优势,它至少说明了不应该再摆弄变量

    如果
    Foo
    是不可移动的,并且复制成本很高,那么是的,那么可能有理由动态分配内存。而且,如果要动态分配内存,最好使用
    std::unique\u ptr
    管理内存

    离题:

    • 在第一个示例中,请注意在
      GetWibble
      中取消对
      wibble
      的引用。您是否保证
      wibble
      不为空?它不可能被设置,也可能被显式设置为
      nullptr
      ,也许这是调用
      GetWibble
      的先决条件,但它是一个例子,说明了指针的额外间接定向如何增加复杂性
    • 在第二个示例中,
      SetWibble
      采用常量引用更为惯用

    您可能会发现这一点很有趣:这次我将仔细阅读这篇文章,我想我之前已经被引导到了这一点……您忘记了,在一种情况下,您使用的是堆,而在另一种情况下,使用的是堆栈,选择取决于应用程序。在第二个示例中,我假设
    Wobble
    中的成员变量
    wibble
    是一个值,而不是一个引用?即
    Wobble::SetWibble
    复制?
    Foo createFoo() {
        Foo foo;
        foo.something = ...;
        foo.something1 = ...;
        foo.something2 = ...;
        return foo;
    }
    
    int main() {
        Wobble wobble;
        wobble.SetWibble(createFoo());
    } 
    
    int main() {
        Wobble wobble;
    
        Foo foo;
        foo.something = ...;
        foo.something1 = ...;
        foo.something2 = ...;
    
        wobble.SetWibble(std::move(foo));
    }