小议iOS中的浅复制和深复制

前言:

提到iOS中的浅复制和深复制的区别,大家都知道浅复制过来的是对象的地址,而深复制,相当于重新开辟了内存空间,存储这个对象。


用代码说话

①单个对象的浅复制与深复制

/// 单个对象 浅复制、深赋值
- (void)ordinaryCopyVSMutableCopy {
    
    NSString *str = @"hehe";
    NSLog(@"源字符:%p",str);
    
    //浅
    NSString *cStr = [str copy];
    NSLog(@"浅复制: Cstr = %p",cStr);
    
    NSString *temp = [str copyWithZone:nil];
    NSLog(@"copyWithZone: temp = %p",temp);
    
    //深
    NSString *mStr = [str mutableCopy];
    NSLog(@"深复制: mStr = %p",mStr);
}

输出结果:

单个对象深浅复制输出结果.png

tips:可以看到 copycopyWithZone方法都是浅复制,对象的地址并没有改变,而mutableCopy重新开辟了内存控件,是深复制

数组及集合类对象的浅复制、深复制、完全复制

我们先定义一个原始数组

NSArray *originArr = [NSArray arrayWithObjects:@"1",@"2", nil];
NSLog(@"原数组 地址:%p",originArr);
NSLog(@"原数组中对象的地址: %p,%p \n",originArr[0],originArr[1]);

看代码:

①对数组进行浅复制
//对数组进行浅复制
  NSArray *copyArr = [originArr copy];
  NSLog(@"浅复制 地址:%p",copyArr);
  NSLog(@"浅复制数组中对象的地址: %p,%p \n",copyArr[0],copyArr[1]);

对比输出结果看:

数组浅复制结果对比.png

tips:可以看到 不论是数组本身还是数组中的元素,地址都没有发生变化,这就是完完全全的浅复制
那么问题1:[NSArray arrayWithArray:originArr] 是浅复制 还是 深复制呢

 NSArray *arr = [NSArray arrayWithArray:originArr];
 NSLog(@"arrayWithArray深复制 地址:%p",arr);
 NSLog(@"arrayWithArray深复制数组中对象的地址: %p,%p \n",arr[0],arr[1]);

结果:

arrayWithArray结果.png

tips:arr相比于源数组,算是一次深复制,但是数组中的元素地址依旧没有发生变化

②对数组进行深复制
 NSArray *mCopyArr = [originArr mutableCopy];
 NSLog(@"深复制 地址:%p",mCopyArr);
 NSLog(@"深复制数组中对象的地址: %p,%p \n",mCopyArr[0],mCopyArr[1]);

打印地址发现:

数组深复制.png
]
可以发现mCopyArr相比于原先的数组算是深复制了,但是内部的元素依旧是原先数组中的元素

问题2:[[NSArray alloc] initWithArray:.... copyItems:true] 是浅复制 还是 深复制呢

 NSArray *array = [[NSArray alloc] initWithObjects:[[NSMutableString alloc] initWithString:@"1"], @"2",nil];
 NSLog(@"array 地址: %p",array);
 NSLog(@"array中元素的地址 :%p,%p",array[0],array[1]);
    
 NSArray *arrWithCopyItem = [[NSArray alloc] initWithArray:array copyItems:true];
 NSLog(@"arrWithCopyItem深复制 地址:%p",arrWithCopyItem);
 NSLog(@"arrWithCopyItem深复制数组中对象的地址: %p,%p \n",arrWithCopyItem[0],arrWithCopyItem[1]);

输出结果:

copyItems深复制、浅复制测试.png

可以看到,arrWithCopyItem对于源数组array中的可变对象进行的是深复制,对不可变对象做的是浅复制,所以可以称,[[NSArray alloc] initWithArray:.... copyItems:true]方法是与源数组做了一次不完全的深复制,对于其中的不可变对象依旧是浅复制
tips:字典的[NSDictionary alloc] initWithDictionary:... copyItems:..这个方法结果同上

问题来了:这不算真正意义上的深复制,即完全复制,那用什么方法可以实现完全复制呢?

②对数组进行完全复制

方法有很多种,这里简单介绍两种:
一:归档、解挡操作

NSData *data = [NSKeyedArchiver archivedDataWithRootObject:originArr];
NSData *aData = [NSKeyedUnarchiver unarchiveObjectWithData:data];
NSArray *mmCopyArr = (NSArray *)aData;
NSLog(@"①归档深复制 地址:%p",mmCopyArr);
NSLog(@"①归档深复制数组中对象的地址: %p,%p \n",mmCopyArr[0],mmCopyArr[1]);
源数组.png

归档、解档后.png

可以看到,不仅数组本身为深复制,数组中的元素也都重新开辟了内存空间

二:对数组进行遍历深复制,该方法较为简单,就不写代码了

Github项目地址

点击去我的Github下载Demo

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 211,265评论 6 490
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,078评论 2 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 156,852评论 0 347
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,408评论 1 283
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,445评论 5 384
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,772评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,921评论 3 406
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,688评论 0 266
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,130评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,467评论 2 325
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,617评论 1 340
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,276评论 4 329
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,882评论 3 312
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,740评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,967评论 1 265
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,315评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,486评论 2 348

推荐阅读更多精彩内容

  • 1. 属性中copy与strong特性的区别 在开始学习浅复制(Shallow Copy)、深复制(Deep Co...
    pro648阅读 1,709评论 2 16
  • 1、对象拷贝有两种方式:浅复制和深复制。顾名思义,浅复制,并不拷贝对象本身,仅仅是拷贝指向对象的指针;深复制是直接...
    滴答大阅读 760评论 0 2
  • 本文为转载: 作者:zyydeveloper 链接://www.greatytc.com/p/5f776a...
    Buddha_like阅读 864评论 0 2
  • A:我要创业啦! B:就你… A:嗯,我要超越马云… B:哈哈…你要超越马云…我还超越秦始皇那… A:真的,我在做...
    我重生阅读 255评论 0 0
  • 成安二中阅读 145评论 0 0