浅复制:只复制指向对象的指针,而不复制引用对象本身。对于浅复制来说,A和A_copy指向的是同一个内存资源,复制的只是一个指针,对象本身资源还是只有一份(对象引用计数+1),那如果我们对A_copy执行了修改操作,那么发现A引用的对象同样被修改了。

深复制就好理解了,内存中存在了两份独立对象本身。

在Objective-C中并不是所有的对象都支持Copy,MutableCopy,遵守NSCopying协议的类才可以发送Copy消息,遵守NSMutableCopying协议的类才可以发送MutableCopy消息。

(一).对非集合类对象的copy操作:

在非集合类对象中:

1、对immutable对象进行copy操作,是指针复制,mutableCopy操作时内容复制;

2、对mutable对象进行copy和mutableCopy都是内容复制。

用代码简单表示如下:

[immutableObject copy] //浅复制

[immutableObject mutableCopy] //深复制

[mutableObject copy] //深复制

[mutableObject mutableCopy] //深复制

代码:

NSString*string =@"origin";

NSString*stringCopy = [stringcopy];//浅复制复制后的对象不可变

NSMutableString*mStringCopy = [stringmutableCopy];//深复制复制后的对象可变

NSLog(@"%p - %p - %p", string, stringCopy, mStringCopy);

2016-03-03 14:56:44.068 Copy[18197:493711] 0x100001080 - 0x100001080 - 0x1003003e0

查看结果:stringCopy和string的内存地址是一样的,mStringCopy和string的内存地址是不一样的。

NSMutableString*string2 = [NSMutableStringstringWithString:@"origin2"];

NSString*stringCopy2 = [string2copy];//深复制复制后的对象不可变

NSMutableString*mStringCopy2 = [string2mutableCopy];//深复制复制后的对象可变

NSLog(@"%p - %p - %p", string2, stringCopy2, mStringCopy2);

2016-03-03 14:56:44.068 Copy[18197:493711] 0x100103920 - 0x326e696769726f75 - 0x1001039b0

查看结果:mStringCopy2、stringCopy2和string2的内存地址都是不一样的。

(二)、集合类对象的copy与mutableCopy

[immutableObject copy] //浅复制

[immutableObject mutableCopy] //单层深复制

[mutableObject copy] //单层深复制

[mutableObject mutableCopy] //单层深复制

代码:

NSArray*array =@[@[@"a",@"b"],@[@"c",@"d"]];

NSArray*copyArray = [arraycopy];//浅复制复制后的对象不可变

NSMutableArray*mCopyArray = [arraymutableCopy];//单层深复制复制后的对象可变

NSLog(@"%p - %p - %p", array, copyArray, mCopyArray);

2016-03-03 14:56:44.069 Copy[18197:493711] 0x100600450 - 0x100600450 - 0x1006038e0

查看结果:copyArray和array的内存地址是一样的,mCopyArray和array的内存地址是不一样的。

NSMutableArray*array2 = [NSMutableArrayarrayWithObjects:[NSMutableStringstringWithString:@"a"],@"b",@"c",nil];

NSArray*copyArray2 = [arraycopy];//单层深复制复制后的对象不可变

NSMutableArray*mCopyArray2 = [arraymutableCopy];//单层深复制复制后的对象可变

NSLog(@"%p - %p - %p", array2, copyArray2, mCopyArray2);

2016-03-03 14:56:44.069 Copy[18197:493711] 0x100106fd0 - 0x100600450 - 0x100107020

查看结果:mCopyArray2、copyArray2和array2的内存地址都是不一样的。

(三)、自定义对象的copy

.h文件

@interfaceComplex :NSObject<NSCopying>//采用NSCoping协议,实现深层拷贝

{

int_real;

int_imaginary;

}

- (void)setReal:(int)real andImg:(int)img;

- (void)Show;

@end

.m文件

@implementationComplex

-(void)setReal:(int)real andImg:(int)img

{

_real= real;

_imaginary= img;

}

-(void)Show

{

NSLog(@"%d+%di",_real,_imaginary);

}

#pragma mark - NSCopying

-(id)copyWithZone:(NSZone*)zone

{

Complex*p = [ComplexallocWithZone:zone];//申请一块Complex的内存

[psetReal:_realandImg:_imaginary];//拷贝数据

returnp;

}

@end

NSLog(@"------------浅拷贝--------------");

Complex*com1 = [[Complexalloc]init];

[com1setReal:12andImg:3];

//浅拷贝

Complex*com2 = com1;

[com1Show];

[com2Show];

2016-03-03 15:23:43.627 Copy[18424:509266] 12+3i

2016-03-03 15:23:43.627 Copy[18424:509266] 12+3i

[com1setReal:3andImg:5];// com1重新赋值

[com1Show];

[com2Show];

// com1重新赋值,com2随之变化

2016-03-03 15:23:43.627 Copy[18424:509266] 3+5i

2016-03-03 15:23:43.627 Copy[18424:509266] 3+5i

[com2setReal:10andImg:5];// com2重新赋值

[com1Show];

[com2Show];

// com2重新赋值,com1也随之变化

2016-03-03 15:23:43.628 Copy[18424:509266] 10+5i

2016-03-03 15:23:43.628 Copy[18424:509266] 10+5i

NSLog(@"------------深拷贝------------");

Complex*comA = [[Complexalloc]init];

[comAsetReal:2andImg:3];

Complex*comB = [comAcopy];//深层拷贝,使用copy方法,但是前提必须实现NSCopying协议中的copyWithZone方法

[comAShow];

[comBShow];

2016-03-03 15:23:43.628 Copy[18424:509266] 2+3i

2016-03-03 15:23:43.628 Copy[18424:509266] 2+3i

[comAsetReal:3andImg:4];// comA重新赋值

[comAShow];

[comBShow];

// comA改变不引起comB变化

2016-03-03 15:23:43.628 Copy[18424:509266] 3+4i

2016-03-03 15:23:43.628 Copy[18424:509266] 2+3i

[comBsetReal:100andImg:2];// comB重新赋值

[comAShow];

[comBShow];

// comB改变不引起comA变化

2016-03-03 15:23:43.628 Copy[18424:509266] 3+4i

2016-03-03 15:23:43.628 Copy[18424:509266] 100+2i

iOS-深复制(mutableCopy)与浅复制(copy)的更多相关文章

  1. Java中的深拷贝(深复制)和浅拷贝(浅复制)

    深拷贝(深复制)和浅拷贝(浅复制)是两个比较通用的概念,尤其在C++语言中,若不弄懂,则会在delete的时候出问题,但是我们在这幸好用的是Java.虽然java自动管理对象的回收,但对于深拷贝(深复 ...

  2. JAVA深复制(深克隆)与浅复制(浅克隆)

    1.浅复制与深复制概念⑴浅复制(浅克隆)被复制对象的所有变量都含有与原来的对象相同的值,而所有的对其他对象的引用仍然指向原来的对象.换言之,浅复制仅仅复制所考虑的对象,而不 复制它所引用的对象. 1. ...

  3. iOS 集合的深复制与浅复制

    概念 对象拷贝有两种方式:浅复制和深复制.顾名思义,浅复制,并不拷贝对象本身,仅仅是拷贝指向对象的指针:深复制是直接拷贝整个对象内存到另一块内存中. 一图以蔽之 再简单些说:浅复制就是指针拷贝:深复制 ...

  4. iOS 浅复制和深复制的深层理解,含示例

    转载:https://www.zybuluo.com/MicroCai/note/50592 版权归 @MicroCai 所有 以下是正文: 浅复制就是指针拷贝:深复制就是内容拷贝. 集合的浅复制 ( ...

  5. 复制对象(一)copy和mutableCopy方法

    本文转载至 http://www.tuicool.com/articles/Fn6rMn CSDN博客原文  http://blog.csdn.net/u010962810/article/detai ...

  6. 也来谈一谈js的浅复制和深复制

    1.浅复制VS深复制 本文中的复制也可以称为拷贝,在本文中认为复制和拷贝是相同的意思.另外,本文只讨论js中复杂数据类型的复制问题(Object,Array等),不讨论基本数据类型(null,unde ...

  7. js的浅复制和深复制

    1.浅复制VS深复制 本文中的复制也可以称为拷贝,在本文中认为复制和拷贝是相同的意思.另外,本文只讨论js中复杂数据类型的复制问题(Object,Array等),不讨论基本数据类型(null,unde ...

  8. js中的深复制与浅复制

    前言 所谓深复制与浅复制(深拷贝与浅拷贝),乍一听感觉听高大上,像是一个非常难理解的概念,其实我们平常项目开发都是在用的,只是你可能不知道该怎么叫它的名字而已,就像你听熟了一首歌,就是不知道这首歌叫什 ...

  9. Python赋值、浅复制和深复制

    Python赋值.浅复制和深复制 ​ 首先我们需要知道赋值和浅复制的区别: 赋值和浅复制的区别 赋值,当一个对象赋值给另一个新的变量时,赋的其实是该对象在栈中的地址,该地址指向堆中的数据.即赋值后,两 ...

随机推荐

  1. VS2015开发环境配置

    1.安装VS2015 Professional(专业版),按需勾选必要项(VC.C#.WEB.GIT) Visual Basic 2015 00322-50050-03552-AA642Microso ...

  2. 【Stage3D学习笔记续】真正的3D世界(四):空间大战雏形

    前面几个星期抽空用Starling做了一个打飞机的小游戏(所以没有接着看书了),准备面试时用的,结果面试还是没过%>_<%...这个游戏打算过几天全部开源了 那么接下来打算这周把<S ...

  3. C++学习笔记(十二):类继承、虚函数、纯虚函数、抽象类和嵌套类

    类继承 在C++类继承中,一个派生类可以从一个基类派生,也可以从多个基类派生. 从一个基类派生的继承称为单继承:从多个基类派生的继承称为多继承. //单继承的定义 class B:public A { ...

  4. cas 3.5.2 登录成功后,如何返回用户更多信息?

    国内私募机构九鼎控股打造APP,来就送 20元现金领取地址:http://jdb.jiudingcapital.com/phone.html内部邀请码:C8E245J (不写邀请码,没有现金送)国内私 ...

  5. 【54】让自己熟悉包括TR1在内的标准程序库

    1.C++0X,不确定哪一年出来,意指200X版的C++ 2.C++标准程序库的主要机能有:STL,iostreams,locals等. 3.TR1:Technical Report 1,只是一份规范 ...

  6. 全局唯一ID的生成方式

    一.程序直接生成: 使用jdk中的concurrent包可以轻松实现唯一数字型ID的生成,且无需考虑单例.采用高效率的CAS无需考虑synchronized关键字 import java.util.c ...

  7. android判断当前应用程序处于前台还是后台

    /**     *判断当前应用程序处于前台还是后台     *      * @param context * @return         */    public static boolean ...

  8. 关于 ioctl 的 FIONREAD 參数

    ioctl 是用来设置硬件控制寄存器,或者读取硬件状态寄存器的数值之类的.而read,write 是把数据丢入缓冲区,硬件的驱动从缓冲区读取数据一个个发送或者把接收的数据送入缓冲区. ioctl(ke ...

  9. sphinx配置文件继承

    # # Minimal Sphinx configuration sample (clean, simple, functional) # source mysql { type = mysql #数 ...

  10. Android应用在不同版本间兼容性处理

    在Android系统中向下兼容性比较差,但是一个应用APP经过处理还是可以在各个版本间运行的.向下兼容性不好,不同版本的系统其API版本也不同,自然有些接口也不同,新的平台不能使用旧的API,旧的平台 ...