C++中字符串的深拷贝与浅拷贝

  在C++中,字符串是用String类型定义的,字符串拷贝分为浅拷贝(位拷贝)和深拷贝两种,下面给出了深拷贝的两种不同的实现方式(普通版和简洁版)

浅拷贝

首先什么是浅拷贝?

  浅拷贝又称为位拷贝,编译器只是将对象中的值拷贝过来,如果对象中管理了资源,就会导致多个对象共享同一份资源,当释放时就会进行多次释放造成程序错误。

class String
{
public:
	String(const char* pStr = "")
	{
		//若指针为空,就让指针指向一个空字符串
		if (NULL == pStr)
		{
			pStr = "";
		}
		//开辟空间,将参数的内容拷贝到类的_pStr中
		_pStr = new char[strlen(pStr) + 1];
		strcpy(_pStr, pStr);
	}
	~String()
	{
		if (_pStr)
			delete[] _pStr;
	}
private:
	char* _pStr;
};

int main()
{
	String s1("hello");
	//拷贝构造函数和赋值函数只进行值拷贝,
	//两个对象共用同一块空间,对象销毁时就会发生内存访问违规
	String s2(s1);
	String s3;
	s3 = s1;
	return 0;
}

如下图:两个对象共用同一块空间(0x007e4e98),对象销毁时就会释放两次从而发生内存访问违规


深拷贝

看完了浅拷贝,也知道它如果管理了资源进行浅拷贝就会发生错误,那什么是深拷贝呢?

深拷贝指的是每个对象拥有自己独立的资源,必须程序员显式的提供拷贝构造函数和赋值运算符重载,这样对象销毁时就不会发生内存违规操作

深拷贝有两种实现方式

1)普通版:为每一个对象开辟一个新的空间

class String
{
public:
	String(const char* pStr = "")
	{
		//若指针为空,就让指针指向一个空字符串
		if (NULL == pStr)
		{
			pStr = "";
		}
		//开辟空间,将参数的内容拷贝到类的_pStr中
		_pStr = new char[strlen(pStr) + 1];
		strcpy(_pStr,pStr);
	}

	//普通版拷贝构造函数,开辟一个新的空间
	String(const String& s)
		:_pStr(new char[strlen(s._pStr)+1])
	{
		strcpy(_pStr, s._pStr);
	}

	//赋值操作符重载,普通版
	String& operator=(const String& s)
	{
		if (this != &s)
		{
			char* pStr = new char[strlen(s._pStr) + 1];
			strcpy(pStr, s._pStr);
			delete _pStr;
			_pStr = pStr;
		}
		return *this;
	}

	~String()
	{
		if (_pStr)
			delete[] _pStr;
	}
private:
	char* _pStr;
};

2)简洁版:(调用构造函数创建临时对象,用临时对象和当前对象交换成员变量)

class String
{
public:
	String(const char* pStr = "")
	{
		//若指针为空,就让指针指向一个空字符串
		if (NULL == pStr)
		{
			pStr = "";
		}
		//开辟空间,将参数的内容拷贝到类的_pStr中
		_pStr = new char[strlen(pStr) + 1];
		strcpy(_pStr,pStr);
	}

	//简洁版拷贝构造函数
	String(const String&s)
		:_pStr(NULL)
	{
		String strTemp(s._pStr);
		swap(_pStr, strTemp._pStr);
	}

	//简洁版,赋值操作符重载
	String& operator=(String& s)
	{
		if (this != &s)
		{
			String strTemp(s._pStr);
			swap(_pStr, strTemp._pStr);
		}
		return *this;
	}

	~String()
	{
		if (_pStr)
			delete[] _pStr;
	}
private:
	char* _pStr;
};
  • 5
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值