事关赋值运算符和复制运算符的区别。
请看下面的代码样例。
重载赋值运算符
HelloWorld& operator=(const HelloWorld& other){
cout<<"~overload"<<endl;
if (this != &other){
*ptr = *other.ptr;
}
return *this;
}
赋值方法1(出问题的写法)
simple_audio::HelloWorld a = simple_audio::HelloWorld();
*a.ptr = 30;
simple_audio::HelloWorld b = a;
cout<< "a->ptr => " << a.ptr <<endl;
*a.ptr = 40;
cout<< "b->ptr => " << b.ptr << "=>" << *b.ptr <<endl;
输出结果:
a->ptr => 0x1e409cf05f0
b->ptr => 0x1e409cf05f0=>40
这里没有打印输出~overload
, 说明重载赋值运算符那个方法没有执行。
并且两个指针指向了同一个地址,说明发生了浅拷贝。
赋值方法2(没出问题)
simple_audio::HelloWorld a = simple_audio::HelloWorld();
*a.ptr = 30;
simple_audio::HelloWorld b;
b = a;
cout<< "a->ptr => " << a.ptr <<endl;
*a.ptr = 40;
cout<< "b->ptr => " << b.ptr << "=>" << *b.ptr <<endl;
结果:
~overload
a->ptr => 0x1cd8fc106e0
b->ptr => 0x1cd8fc10790=>30
这里执行了,并且没有发生浅拷贝。
原因
写法1进行对象初始化操作,直接调用复制运算符。而写法2是对对象b初始化后,对对象b赋值a,调用的是赋值运算符。所以写法1的时候需要重载复制运算符。
HelloWorld(const HelloWorld& other){
cout<<"~~resign"<<endl;
this->ptr = new int(*other.ptr);
}
结果
~~resign
a->ptr => 0x21f0011c350
b->ptr => 0x21f0011c380=>30