浅拷贝和深拷贝
2016-10-22 12:52
141 查看
一、浅拷贝和深拷贝
所谓浅拷贝,就是由默认的拷贝构造函数所实现的对数据成员逐一赋值。若类中含有指针类型的数据,这种方式只是简单的把指针的指向赋值给新成员,但并没有给新成员分配内存,因此这种方式必然会导致错误。为了解决浅拷贝出现的错误,必须显示的定义一个拷贝构造函数,使之不但复制数据成员,而且为对象分配各自的内存空间,这就是所谓的深拷贝。
二、浅拷贝
浅拷贝就是由默认的拷贝构造函数所实现的数据成员逐一赋值。通常默认的拷贝构造函数能够胜任这个工作,但是若类中含有指针类型的数据,这种数据成员逐一赋值的方式将会产生错误。
例:
[cpp] view
plain copy
class Student
{
public:
Student( char *name ,int age) //构造函数
{
_name = new char [10]; //分配内存
strcpy(_name, name);
_age = age;
}
~Student()
{
delete[] _name; //释放动态内存
}
void display()
{
cout << _name << "--" << _age << endl;
}
private:
char *_name;
int _age;
};
int main()
{
Student st1("lisi" , 20);
Student st2(st1); //调用默认的拷贝构造函数创建一个新的对象
system( "pause");
return 0;
}
[align=left]
[/align]
程序运行,创建st1时调用构造函数 ,用运算符new从堆上分配一块空间,并用_name指向这块内存空间。在执行st2语句时,因为没有定义拷贝构造函数,所以调用默认的拷贝构造函数:
[align=left] Student( Student& st )[/align]
[align=left] {[/align]
_name = st._name;
//并没有为对象st2的数据成员_name分配新的内存空间
[align=left] _age = st._age;[/align]
[align=left] }[/align]
主程序结束时,对象被逐个撤销,先撤销对象st2(因为st2后创建),撤销前先调用析构函数,用delete运算符释放所分配的内存空间;撤销对象st1时,第二次调用析构函数,因为这时_name所指向的内存空间已经被释放,企图对同一块内存空间释放两此,所以这时候程序出错。
执行过程如图:
三、深拷贝
为了解决浅拷贝出现的错误,必须显示的定义一个拷贝构造函数,使之不但能复制数据成员,而且为指针分配各自的动态内存。
例:
[cpp] view
plain copy
class Student
{
public:
Student( char *name ,int age) //构造函数
{
_name = new char [10]; //分配内存
strcpy(_name, name);
_age = age;
}
Student( Student& st ) //自定义的拷贝构造函数
{
_name = new char [10];
if (_name != NULL )
{
strcpy(_name, st._name);
_age = st._age;
}
}
~Student()
{
delete[] _name; //释放动态内存
}
void display()
{
cout << _name << "--" << _age << endl;
}
private:
char *_name;
int _age;
};
int main()
{
Student st1("lisi" , 20);
Student st2(st1); //调用默认的拷贝构造函数创建一个新的对象
system( "pause");
return 0;
}
在执行Student st2(st1)时调用自定义的拷贝构造函数,为st2._name分配自己的动态内存。程序的执行过程如图:
转载地址:http://blog.csdn.net/lf_2016/article/details/51985464?ref=myread
顶2
踩1
所谓浅拷贝,就是由默认的拷贝构造函数所实现的对数据成员逐一赋值。若类中含有指针类型的数据,这种方式只是简单的把指针的指向赋值给新成员,但并没有给新成员分配内存,因此这种方式必然会导致错误。为了解决浅拷贝出现的错误,必须显示的定义一个拷贝构造函数,使之不但复制数据成员,而且为对象分配各自的内存空间,这就是所谓的深拷贝。
二、浅拷贝
浅拷贝就是由默认的拷贝构造函数所实现的数据成员逐一赋值。通常默认的拷贝构造函数能够胜任这个工作,但是若类中含有指针类型的数据,这种数据成员逐一赋值的方式将会产生错误。
例:
[cpp] view
plain copy
class Student
{
public:
Student( char *name ,int age) //构造函数
{
_name = new char [10]; //分配内存
strcpy(_name, name);
_age = age;
}
~Student()
{
delete[] _name; //释放动态内存
}
void display()
{
cout << _name << "--" << _age << endl;
}
private:
char *_name;
int _age;
};
int main()
{
Student st1("lisi" , 20);
Student st2(st1); //调用默认的拷贝构造函数创建一个新的对象
system( "pause");
return 0;
}
[align=left]
[/align]
程序运行,创建st1时调用构造函数 ,用运算符new从堆上分配一块空间,并用_name指向这块内存空间。在执行st2语句时,因为没有定义拷贝构造函数,所以调用默认的拷贝构造函数:
[align=left] Student( Student& st )[/align]
[align=left] {[/align]
_name = st._name;
//并没有为对象st2的数据成员_name分配新的内存空间
[align=left] _age = st._age;[/align]
[align=left] }[/align]
主程序结束时,对象被逐个撤销,先撤销对象st2(因为st2后创建),撤销前先调用析构函数,用delete运算符释放所分配的内存空间;撤销对象st1时,第二次调用析构函数,因为这时_name所指向的内存空间已经被释放,企图对同一块内存空间释放两此,所以这时候程序出错。
执行过程如图:
三、深拷贝
为了解决浅拷贝出现的错误,必须显示的定义一个拷贝构造函数,使之不但能复制数据成员,而且为指针分配各自的动态内存。
例:
[cpp] view
plain copy
class Student
{
public:
Student( char *name ,int age) //构造函数
{
_name = new char [10]; //分配内存
strcpy(_name, name);
_age = age;
}
Student( Student& st ) //自定义的拷贝构造函数
{
_name = new char [10];
if (_name != NULL )
{
strcpy(_name, st._name);
_age = st._age;
}
}
~Student()
{
delete[] _name; //释放动态内存
}
void display()
{
cout << _name << "--" << _age << endl;
}
private:
char *_name;
int _age;
};
int main()
{
Student st1("lisi" , 20);
Student st2(st1); //调用默认的拷贝构造函数创建一个新的对象
system( "pause");
return 0;
}
在执行Student st2(st1)时调用自定义的拷贝构造函数,为st2._name分配自己的动态内存。程序的执行过程如图:
转载地址:http://blog.csdn.net/lf_2016/article/details/51985464?ref=myread
顶2
踩1
相关文章推荐
- SQL SERVER 同表跨连接拷贝数据
- 运算符之深度复制拷贝
- JavaIo流,文件文件夹拷贝工具类
- ios深浅拷贝学习
- C++深浅拷贝浅析
- iOS 深拷贝两种实现
- 网页禁用右键、防拷贝及"另存为"失效方法
- C++拷贝构造函数(深拷贝,浅拷贝)
- 解决浅拷贝的几种方式
- ios 深浅拷贝学习
- C++ 浅拷贝与深拷贝浅析
- Github 开源:高效好用的对象间属性拷贝工具:升讯威 Mapper( Sheng.Mapper)
- 实现NSDictionary的深层拷贝
- 使用strcpy拷贝字符串因分配空间不足导致漏洞
- C# 文件夹拷贝
- 利用分页锁定主机存储器进行主机与设备之间的0拷贝
- IO流第七课,字符流、纯文本、节点流,Reader、FileReader、Writer、FileWriter读取、写出、拷贝
- 拷贝、赋值和销毁
- 两种关闭拷贝构造的手法
- SAP的集团拷贝(Client Copy)--目前主要是本地copy