ptr behaviour while passing through function

In below code snippet i am getting segmentation fault while passing unique_ptr as as value. usually this is known issue with auto_ptr as due to ownership issue (Assignee pointer becomes NULL) it can't be accessed after assignment. but why i am facing the same issue with unique_ptr even though it is having move semantics.

what i understood auto_ptr use copy constructor and unique_ptr use move function to transfer the ownership. But in both cases assignee pointer becomes null then what is the significance of having move semantics here. I believe compiler should flash the error if unique_ptr is passed as a value like below statement as copy constructor is private in unique_ptr. could you throw some light on this regarding this behaviour.

unique_ptr<Test> a = p;//deleted function (copy constructor).

Here is the code snippet:

#include<iostream>

#include<memory>

using namespace std;

class Test
{
public:
    Test(int a = 0 ) : m_a(a)
    {
    }
    ~Test( )
    {
        cout<<"Calling destructor"<<endl;
    }

    int m_a;
};


//***************************************************************
void Fun(std::unique_ptr<Test> p1 )
{
    cout<<p1->m_a<<endl;
}
//***************************************************************
int  main( )
{
    std::unique_ptr<Test> p( new Test(5) );
    Fun(std::move(p));
    cout<<p->m_a<<endl;

    return 0;
}

By writing std::move(p) you are casting p to an r-value reference. unique_ptr has a constructor that takes an r-value reference (a move constructor) so it constructs the by-value parameter using this move constructor and there is no compilation error.

You should not pass a unique_ptr by value unless you want to transfer ownership.

If you transfer ownership then the unique_ptr in the outer scope does not own anything anymore and it is undefined behaviour to dereference it.

In this case you should pass Test by const reference:

void fun(const Test& t) {
    std::cout << t.m_a << std::endl;
} 

int main(){
    auto p = std::make_unique<Test>(5);
    fun(*p);
}

See here for more information about how to pass smart pointers in general.


The deleted copy constructor is not involved here. unique_ptr has a move constructor which is used, because you explicitly requested a move from the source with std::move .

You shouldn't be using the moved-from value except to destroy it out assign to it.

It's not an error. A compiler could warn, but since you have explicitly moved it may reasonably assume that you know what you are doing.


Instead of using unique_ptr as a value , pass the same as a reference . You create a unique pointer. You then construct another unique_ptr from that one, using the move constructor. So the original gets set to null. That's what happens when you move a unique_ptr. Honestly speaking as i didn't get chance work with auto_ptr so can't comment on this behavior.

void Fun( const std::unique_ptr<Test>& p1 )
{
 cout<<p1->ma;
}
链接地址: http://www.djcxy.com/p/59684.html

上一篇: 你如何计算Visual Studio解决方案中的代码行数?

下一篇: ptr行为,同时通过函数