viv*_*an2 3 c++ unique-ptr move-semantics c++11
我正在尝试使用unique_ptr并编写一些简单的代码来检查它如何与移动语义一起工作.
#include <iostream>
#include <vector>
using namespace std;
class X
{
public:
X(){}
~X() { cout << "Destructor X" << endl; }
void Print() { cout << "X" << endl; }
};
int main()
{
unique_ptr<X> ptr(new X());
ptr->Print();
vector<unique_ptr<X>> v;
v.push_back(move(ptr));
ptr->Print();
v.front()->Print();
return 0;
}
Run Code Online (Sandbox Code Playgroud)
输出如下:
X
X
X
Destructor X
Run Code Online (Sandbox Code Playgroud)
我的期望是原始的unique_ptr ptr在push_back之后会失效.但Print()方法被调用就好了.这种行为会有什么解释?
Jon*_*ely 12
我的期望是原始的unique_ptr ptr在push_back之后会失效.
它被设置为空指针.您可以通过比较来检查nullptr.
但这个
Print()方法被称为正常.这种行为会有什么解释?
您正在调用空指针上的成员函数,这是未定义的行为.该成员函数实际上并不访问类中的任何数据,因此它不会崩溃,但它仍然是未定义的行为.
你得到这个程序的类似行为,它与unique_ptr以下内容无关:
int main()
{
X x;
X* ptr = &x;
ptr->Print();
ptr = nullptr;
ptr->Print();
}
Run Code Online (Sandbox Code Playgroud)
它似乎工作正常,因为X::Print()实际上没有从this指针读取任何东西.如果更改了X::Print()访问类中某些成员数据的定义,则可能会因解除引用空指针而崩溃.
请参阅何时在null实例上调用成员函数会导致未定义的行为?欲获得更多信息.
你所拥有的是明确未定义的行为.如果我更换的内容main与以下
int main()
{
unique_ptr<X> ptr;
ptr->Print();
cout << (static_cast<bool>(ptr) ? "active\n" : "inactive\n");
}
Run Code Online (Sandbox Code Playgroud)
gcc和clang都打印出来
X
inactive
Run Code Online (Sandbox Code Playgroud)
你正在调用一个成员函数nullptr,我猜它恰好工作,因为成员函数实际上并没有使用this指针.将您的班级定义更改为:
class X
{
int y = 0;
public:
X(){}
~X() { cout << "Destructor X" << endl; }
void Print() { cout << "y = " << y << endl; }
};
Run Code Online (Sandbox Code Playgroud)
现在您的原始代码应该导致分段错误,因为它会尝试取消引用nullptr.
至于unique_ptr你离开它后会失效的期望,你是绝对正确的.这是标准的保证.
§20.8.1/ 4 [unique.ptr]
此外,
u可以根据请求将所有权转移到另一个唯一指针u2.完成此类转移后,以下后置条件成立:
-u2.p等于预转移u.p,
-u.p等于nullptr,
......
Above u&u2是unique_ptr对象,p是指向托管对象的指针.
| 归档时间: |
|
| 查看次数: |
1120 次 |
| 最近记录: |