CPP杂记——移动构造函数中需要注意的问题

首先提一下为什么要使用移动构造函数:
在多次使用传值做参数的方法时,不可避免的会产生临时对象从而调用拷贝构造函数。
.
默认的浅拷贝构造函数在临时变量被析构时还会释放其中的动态元素内存,这时便会对其他部分产生影响,c++11前未仔细优化的代码大都直接编写深拷贝构造函数,但由于作为参数的临时性,这种行为是无必要的。
.
这时的优化方法为使用“右值引用”,通过直接取得传入临时变量的所有权,可令如push_back(tempClass(args…))此类的函数只调用一次构造函数
具体做法:实现参数类型为const T& 或者 T&& 类型的具体方法

1.在移动构造函数中结束对原临时变量的引用时,需要将右值引用设置为nullptr释放原有的临时变量资源,eg:
MyObject& operator=(MyObject&& obj /*const MyObject& obj*/) noexcept {
       delete 		m_pData;
       m_data 		= obj.m_pData;
       obj.m_pData 	= nullptr; 		//释放临时资源
       return *this;
}
2.注意,不能习惯性的在右值引用前加上const,否则仍会导致二次拷贝的调用

…关于const 右值引用的用途,我猜可能是防止编译上的一些问题?比如不让const左值调用右值版本的函数,,?我还是暂且蒙在鼓里

3.最后,1中实现的版本还有着一个重大的问题,即在自身作为参数时会导致源值在函数结束后被释放,eg:
MyObject o(364364);
MyObject b = std::move(o);
cout << (uintptr)o.m_pData << endl;

输出结果为: 0
显然,o中的成员被清除了,这都是由于

obj.m_pData 	= nullptr; 		//释放临时资源

为了避免这种情况需要添加代码为如下形式:

MyObject& operator=(MyObject&& obj /*const MyObject& obj*/) noexcept {
	   //Coco
	   if(&obj == this) return *this;
	   
       delete 		m_pData;
       m_data 		= obj.m_pData;
       obj.m_pData 	= nullptr; 		//释放临时资源
       return *this;
}
发布了24 篇原创文章 · 获赞 14 · 访问量 6123

猜你喜欢

转载自blog.csdn.net/qq_35587463/article/details/105013804
今日推荐