浅拷贝、深拷贝、值拷贝和位拷贝
首先: 位拷贝就是浅拷贝,值拷贝就是深拷贝。
编译器会在必要的时候,自己产生默认的拷贝构造函数和赋值函数,采用的位拷贝。
自己可以重新定义 拷贝构造函数,要注意采用值拷贝。
Q:什么是浅拷贝(shallow copy)和深拷贝(deep copy)?
A: 浅拷贝就是成员数据之间的一一赋值,但是可能会有这样的情况:对象还包含资源,这里的资源可以是堆资源,或者一个文件。当值拷贝的时候,两个对象就有用共同的资源,同时对资源可以访问,这样就会出问题。深拷贝就是用来解决这样的问题的,它把资源也赋值一次,使对象拥有不同的资源,但资源的内容是一样的。对于堆资源来说,就是在开辟一片堆内存,把原来的内容拷贝。
如果你拷贝的对象中引用了某个外部的内容(比如分配在堆上的数据),那么在拷贝这个对象的时候,让新旧两个对象指向同一个外部的内容,就是浅拷贝;如果在拷贝这个对象的时候为新对象制作了外部对象的独立拷贝,就是深拷贝
引用和指针的语义是相似的,引用是不可改变的指针,指针是可以改变的引用。其实都是实现了引用语义。
深拷贝和浅拷贝的区别是在对象状态中包含其它对象的引用的时候,当拷贝一个对象时,如果需要拷贝这个对象引用的对象,则是深拷贝,否则是浅拷贝。
COW语义是“深拷贝”与“推迟计算”的组合,仍然是深拷贝,而非浅拷贝,因为拷贝之后的两个对象的数据在逻辑上是不相关的,只是内容相同。
===========================================================
Q:什么情况下使用浅拷贝什么时候使用深拷贝?
A: 无论深浅,都是需要的。当深拷贝发生时,通常表明存在着一个“聚合关系”,而浅拷贝发生时,通常表明存在着一个“相识关系”。
举个简单的例子:
当你实现一个Composite Pattern,你通常都会实现一个深拷贝(如果需要拷贝的话),很少有要求同的Composite共享Leaf的;
而当你实现一个Observer Pattern时,如果你需要拷贝Observer,你大概不会去拷贝Subject,这时就要实现个浅拷贝。
是深拷贝还是浅拷贝,并不是取决于时间效率、空间效率或是语言等等,而是取决于哪一个是逻辑上正确的。
===========================================================
Q:在C++中default constructor对对象进行的是怎样的拷贝动作?
A: 再纠正一个概念:default constructor是不负责拷贝动作的,我想你说的应该是指implicitly-declared copy constructor。它会调用所有直系基类的copy constructor和有成员的copy constructor,并且复制vtpr。如果一个类:
1:没有虚方法和虚基类
2:所有直系基类的copy constructor都是无代价的
3:所有成员的copy constructor都是无代价的
这时它的copy constructor是无代价的,相当于用memcpy实现。
判 断它是深拷贝还是浅拷贝,还是要根据类的实现。比如如果它有一个用原生指针指针实现的对象引用,或是用boost::shared_ptr等引用分享所有 权的智能指针实现的对象引用,则这个拷贝是浅拷贝;如果是用copy_ptr这种实现了深拷贝的智能指针实现的对象引用,就是深拷贝了。
浅拷贝、深拷贝、值拷贝和位拷贝相关推荐
- C++ 类的深拷贝与浅拷贝||深拷贝通过重载拷贝构造函数与重载赋值运算符实现
http://blog.csdn.net/wangshihui512/article/details/9842225 在面向对象程序设计中,对象间的相互拷贝和赋值是经常进行的操作. 如果对象在申明的同 ...
- 深入浅出解释深拷贝、浅拷贝、对象拷贝、引用拷贝原理和应用
拷贝总体上分为引用拷贝和对象拷贝. 1. 引用拷贝 创建一个指向对象的引用变量的拷贝. public class QuoteCopy {public static void main(String[] ...
- 引用拷贝、对象拷贝、浅拷贝、深拷贝 到底是什么【详细例子介绍】
首先要知道的: Java的数据类型分为基本数据类型和引用数据类型. 拷贝一个对象,可以使用 Cloneable接口的clone()方法. 对象拷贝分为 浅拷贝 和 深拷贝,这两种拷贝都是从引用拷贝 引 ...
- 深入理解Python深拷贝(deepcopy)、浅拷贝(copy)、等号拷贝----看了还不懂找我
编程中难免会遇到copy(浅拷贝)与deepcopy(深拷贝)问题,一不小心就会掉进坑中了,或许很多人只知道有深浅拷贝,但是你又知道copy和"="拷贝有什么区别么?也许很少有人对 ...
- java数组深拷贝和浅拷贝_java中的深拷贝与浅拷贝(值类型 vs 引用类型)
对象赋值 赋值是日常编程过程中最常见的操作,最简单的比如: Student codeSheep = new Student(); Student codePig = codeSheep; 严格来说,这 ...
- 深拷贝与浅拷贝、值语义与引用语义对象语义 ——以C++和Python为例
深拷贝与浅拷贝.值语义与引用语义/对象语义 --以C++和Python为例 值语义与引用语义(对象语义) 本小节参考自:https://www.cnblogs.com/Solstice/archive ...
- python浅拷贝 深拷贝
Python 变量 对象 引用 1.变量 变量第一次赋值时被创建,变量在使用前必须赋值 变量本身没有类型,变量类型为它引用的对象类型: 变量在使用时被替换成它引用的对象 2.对象 对象本身具有计数和类 ...
- Interview:算法岗位面试—10.11下午—上海某公司算法岗位(偏机器学习,互联网数字行业)技术面试考点之XGBoost的特点、python的可变不可变的数据类型、赋值浅拷贝深拷贝区别
ML岗位面试:10.11下午-上海某公司算法岗位(偏机器学习,互联网数字行业)技术面试考点之XGBoost的特点.python的可变不可变的数据类型.赋值浅拷贝深拷贝区别 Interview:算法岗位 ...
- 深度拷贝 java_Java深度拷贝方式和性能对比
前言 Java的深度拷贝大致分为克隆(实现Java的Clone接口)和序列化(实现Java的Serializable接口)两种,但是基于不同的序列化方式,有可以延伸出几种方式.下面分析一下每种的注意事 ...
最新文章
- 破解制造业困局:从实际案例看制造业如何缩短订单交付周期?
- XPath语法 在C#中使用XPath例子与用法
- 【kerberos】kerberos 认证 详情介绍
- java vector 多线程_如何使用vector解决多线程问题(java)
- nginx与lighttpd性能简单对比
- Vissim 中动态交通路径选择
- java list foreach 修改_Java ArrayList在foreach中remove的问题分析
- 让刺猬和狐狸结婚:资本巨鳄BlackRock的金融科技野心
- 如何用Java写一个规范的http接口?
- 抛硬币概率公式 计算机题,行测古典型概率问题:抛硬币
- 《第五项修炼》读后感
- 优秀的 icon 的免费网站,看这篇就够了
- java实验3_Java实验3
- vs运行程序时报错:“XXX处有未经处理的异常: 0xC0000374: 堆已损坏”
- 7-23 币值转换(20 分)
- YesPlayMusic 0.4.0中文版:一款mac用户必备的网易云音乐客户端
- 第五章 循环结构程序设计习题(2)
- 怎样消除公司的信息孤岛
- 圆周率π的前10000位是什么?
- 浅谈动感歌词-歌词分析篇