IOS的浅拷贝和深拷贝
什么是深拷贝和浅拷贝
浅拷贝:就是指针的复制,拷贝的指针跟原指针指向内存中的同一个位置的对象。至于对象的引用计数值是否+1,就是看拷贝的指针赋给给的变量是Strong类型的,还是week类型的。 如果是 strong类型,那么被拷贝的对象的内存计数值会+1,如果赋值给了weak类型的变量,那么被拷贝的对象的内存计数值会保持不便。
深拷贝:将内存中的对象拷贝一份,放到一个新的位置,并将这个指向这个新位置的指针指赋值给另外一个变量。
判断拷贝类型,关键的依据是指针所指向的对象在内存中的地址。
IOS中的拷贝方式有两种拷贝,一种是 copy ,另外一种是mutableCopy。 至于这两种方法对产生的拷贝属于'浅拷贝'还是'深拷贝'是要根据具体情况来决定的。
1:对于非容器类对象的拷贝。
什么是非容器类对象。 类似于 NSString ,NSNumber 等这种只能存储一个值的对象就叫做非容器类对象。
1.1:非容器类不可变对象的拷贝
NSString *string = @"非容器类对象";
NSString *stringCopy = [string copy];
NSMutableString *MStringCopy = [string copy];
NSString *stringMutCopy = [string mutableCopy];
NSMutableString *MStringMutCopy = [string mutableCopy];
NSLog(@"对象的地址:%p",string); //对象的地址:0x107d7e6d8
NSLog(@"对象的地址:%p",stringCopy); //对象的地址:0x107d7e6d8
NSLog(@"对象的地址:%p",MStringCopy); //对象的地址:0x107d7e6d8
NSLog(@"对象的地址:%p",stringMutCopy); //对象的地址:0x7f9f397022e0
NSLog(@"对象的地址:%p",MStringMutCopy); //对象的地址:0x7f9f395043c0
通过上面的打印结果来分析:
对于非容器类不可变对象:copy是属于浅拷贝,mutableCopy属于深拷贝
为什么会这样呢?
复制之后,IOS也是考虑到了内存控制和变量之间不相互干扰的原则。 对于内存中不可变的对象,因为对象不可变,所以对于使用这个对象的变量来说,指向同一个内存位置,即满足了使用相同的内容,又不必要开辟新内存空间,达到了节省内存空间的目的。
1.2:非容器类可变对象的拷贝
NSMutableString *string = [NSMutableString stringWithString:@"非容器类可变对象"];
NSString *stringCopy = [string copy];
NSMutableString *MStringCopy = [string copy];
NSString *stringMutCopy = [string mutableCopy];
NSMutableString *MStringMutCopy = [string mutableCopy];
NSLog(@"对象的地址:%p",string); //对象的地址:0x7fc2c9f054a0
NSLog(@"对象的地址:%p",stringCopy); //对象的地址:0x7fc2c9d08800
NSLog(@"对象的地址:%p",MStringCopy); //对象的地址:0x7fc2c9d168e0
NSLog(@"对象的地址:%p",stringMutCopy); //对象的地址:0x7fc2c9c065e0
NSLog(@"对象的地址:%p",MStringMutCopy); //对象的地址:0x7fc2c9d179b0
可以看到上面的对象在内存中的地址都不相同,也就是说他们发生的拷贝都是深拷贝
总结:
1:对于非容器类不可变对象的拷贝,copy方法属于浅拷贝,mutableCopy属于深拷贝
2:对于非容器类可变对象的拷贝, copy方法属于深拷贝,mutableCopy也属于深拷贝
这样处理的依据是:对象之间的不干扰以及内存节省的原则
2:对于容器类对象的拷贝
什么是容器类对象。就是可以存储其他对象的对象。比如:NSArray,NSDictionary等等
2.1:不可变容器类对象的拷贝
NSArray *ary = [NSArray arrayWithObjects:@"1",@"2",@"3",@"4", nil];
NSArray *aryCopy = [ary copy];
NSMutableArray *MAryCopy = [ary copy];
NSArray *aryMCopy = [ary mutableCopy];
NSMutableArray *MAryMCopy = [ary mutableCopy];
NSLog(@"对象的地址:%p",ary); //0x7fedc25058c0
NSLog(@"对象的地址:%p",aryCopy); //0x7fedc25058c0
NSLog(@"对象的地址:%p",MAryCopy); //0x7fedc25058c0
NSLog(@"对象的地址:%p",aryMCopy); //0x7fedc250b5f0
NSLog(@"对象的地址:%p",MAryMCopy); //0x7fedc2414310
根据对象在内存中的地址可以,
对于不可变容器类对象为,copy为浅拷贝,mutableCopy为神拷贝
2.2:可变容器类对象的拷贝
NSMutableArray *ary = [NSMutableArray arrayWithObjects:@"1",@"2",@"3",@"4", nil];
NSArray *aryCopy = [ary copy];
NSMutableArray *MAryCopy = [ary copy];
NSArray *aryMCopy = [ary mutableCopy];
NSMutableArray *MAryMCopy = [ary mutableCopy];
NSLog(@"对象的地址:%p",ary); //0x7fe703703d90
NSLog(@"对象的地址:%p",aryCopy); //0x7fe703706720
NSLog(@"对象的地址:%p",MAryCopy); //0x7fe703706180
NSLog(@"对象的地址:%p",aryMCopy); //0x7fe7037061b0
NSLog(@"对象的地址:%p",MAryMCopy); //0x7fe703706200
通过拷贝后对象在内存中的地址可以看到,对于可变容器类对象的拷贝,不管copy和mutableCopy都是深拷贝。
IOS的浅拷贝和深拷贝的更多相关文章
- [转] js对象浅拷贝和深拷贝详解
本文为大家分享了JavaScript对象的浅拷贝和深拷贝代码,供大家参考,具体内容如下 1.浅拷贝 拷贝就是把父对像的属性,全部拷贝给子对象. 下面这个函数,就是在做拷贝: var Chinese = ...
- 【转】Python中的赋值、浅拷贝、深拷贝介绍
这篇文章主要介绍了Python中的赋值.浅拷贝.深拷贝介绍,Python中也分为简单赋值.浅拷贝.深拷贝这几种"拷贝"方式,需要的朋友可以参考下 和很多语言一样,Python中 ...
- 渐析java的浅拷贝和深拷贝
首先来看看浅拷贝和深拷贝的定义: 浅拷贝:使用一个已知实例对新创建实例的成员变量逐个赋值,这个方式被称为浅拷贝. 深拷贝:当一个类的拷贝构造方法,不仅要复制对象的所 ...
- 关于JavaScript的浅拷贝和深拷贝
在 JS 中有一些基本类型像是Number.String.Boolean,而对象就是像这样的东西{ name: 'Larry', skill: 'Node.js' },对象跟基本类型最大的不同就在于他 ...
- c#中浅拷贝和深拷贝的理解
c#中拷贝有浅拷贝和深拷贝之分. 例如对象A,其中有值类型字段和引用类型字段: 1.浅拷贝: 对于值类型字段,直接逐位复制到新拷贝的副本对象中,修改副本的字段的值,不会影响源对象中字段的值: 对于引用 ...
- C#浅拷贝与深拷贝区别
也许会有人这样解释C# 中浅拷贝与深拷贝区别: 浅拷贝是对引用类型拷贝地址,对值类型直接进行拷贝. 不能说它完全错误,但至少还不够严谨.比如:string 类型咋说? 其实,我们可以通过实践来寻找答案 ...
- 关于python中赋值、浅拷贝、深拷贝之间区别的深入分析
当重新学习了计算机基础课程<数据结构和算法分析>后再来看这篇自己以前写的博文,发现错误百出.python内置数据类型之所以会有这些特性,归根结底是它采用的是传递内存地址的方式,而不是传递真 ...
- js中的浅拷贝和深拷贝
说说最近所学:浅拷贝和深拷贝也叫做浅克隆和深克隆,深浅主要针对的是对象的"深度",常见的对象都是"浅"的,也就是对象里的属性就是单个的属性,而"深&q ...
- 编写高质量代码改善C#程序的157个建议[为类型输出格式化字符串、实现浅拷贝和深拷贝、用dynamic来优化反射]
前言 本文已更新至http://www.cnblogs.com/aehyok/p/3624579.html .本文主要学习记录以下内容: 建议13.为类型输出格式化字符串 建议14.正确实现浅拷贝和深 ...
随机推荐
- 【Android】Eclipse Memory Analyzer 进行堆内存溢出分析
MAT 不是一个万能工具,它并不能处理所有类型的堆存储文件. 不同厂家的 JVM 所生成的堆转储文件在数据存储格式以及数据存储内容上有很多区别,但是比较主流的厂家和格式,例如 Sun, HP, ...
- paip.powerdesign cdm pdm文件 代码生成器 java web 页面 实现
paip.powerdesign cdm pdm文件 代码生成器 java web 页面 实现 准备从pd cdm生成java web 页面...但是,ms无直接地生成软件.... 只好自己解析cdm ...
- FIR.im Weekly - 上周微博热转资源精选
LeakCanary: 让内存泄露无所遁形 Square 开源的 LeakCanary,国内开发者 @廖祜秋liaohuqiu 翻译了对应的官方博客,撰写了中文使用说明文档,同时还写了一个小 Demo ...
- 使用iMovie和Keynote制作App Preview
App Preview是什么 App Preview就是一段15-30秒的短视频,用来展示你的应用的特性.用户界面.交互方式等内容.在App Store你的应用的详细信息页面里,放在原来的截图之前.体 ...
- Maven学习总结(二)——Maven项目构建过程练习_转载
上一篇只是简单介绍了一下maven入门的一些相关知识,这一篇主要是体验一下Maven高度自动化构建项目的过程 一.创建Maven项目 1.1.建立Hello项目 1.首先建立Hello项目,同时建立M ...
- Android图片处理-相机、相处简单调用
安卓开发中,常常需要使用到手机相机拍照.或者相册上传头像等等.通过使用Intent,我们很方便地获得相机.相册里面的图片: 1.相机调用,通过设置File文件路径和文件名,可以将拍照得到的图片保存下来 ...
- 修復jquery的tablesorter对加了千分位的数字无法正确排序的bug
找到函数: function getElementText(config, node) { var text = ""; if (!node) return "" ...
- cache 浅析
http://blog.chinaunix.net/uid-26817832-id-3244916.html 1. Cache Cache一词来源于法语,其原意是"藏匿处,隐秘的地方&q ...
- [Aaronyang] 写给自己的WPF4.5 笔记18[几何图形*Geometry图文并茂讲解]
为什么要掌握?因为WPF 3D知识很多与它Geometry对比,所以我要系统学一下. --学会用Geometry给Path的Data属性填充. 图形可以转换成路径,Path的值,当然你也可以直接使用R ...
- [2013 eoe移动开发者大会]靳岩:从码农到极客的升级之路
(国内知名Android开发论坛 eoe开发者社区推荐:http://www.eoeandroid.com/) 前天,2013 eoe 移动开发者大会在国家会议中心召开,eoe 开发者社区创始人靳岩在 ...