首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >iOS-Strong/Copy修饰词

iOS-Strong/Copy修饰词

作者头像
用户2215591
发布2018-06-29 14:57:04
4540
发布2018-06-29 14:57:04
举报
文章被收录于专栏:iOSer成长记录iOSer成长记录

在iOS中,string是用strong修饰还是用copy修饰?它们有什么区别呢?本文主要就来讨论这两个问题,在此之前,我们需要知道两个术语,浅拷贝和深拷贝

浅拷贝:指对内存地址的复制,让目标对象指针和源对象指向同一片内存空间,当内存销毁的时候,指向这片内存的指针需要赋值,要不然会成为野指针 深拷贝:指对对象具体内容复制,重新分配对象的内存地址,拷贝结束之后,两个对象虽然值是相同的,但是内存地址不一样,两个对象也互不影响,互不干涉

上代码,测试一下

NSString *str = @"test";
NSString *copyStr = [str copy];
NSMutableString *mutStr = [str mutableCopy];
    
NSLog(@"指针地址:str:%p--copyStr:%p--mutStr:%p",&str,&copyStr,&mutStr);
NSLog(@"内存地址:str:%p--copyStr:%p--mutStr:%p",str,copyStr,mutStr);

运行结果:

指针地址:str:0x16fb31678--copyStr:0x16fb31670--mutStr:0x16fb31668
内存地址:str:0x1002d4080--copyStr:0x1002d4080--mutStr:0x1c024af80

可以看出:copy实现了一次浅拷贝,mutableCopy实现了一次深拷贝 实际上,对于copy和mutableCopy我们可以得出下表的结论

理解了copy作用,我们就不难理解属性中的copy和strong了,实际上在属性中copy比strong多了一步,即在setter方法中

- (void)setName:(id)name{
    _name = [name copy];
}

举个例子:假设有这样一段代码

@property(copy)id obj;

self.obj = object;

此时obj是什么呢?有下面两种情况:
1. object是不可变对象,将会把object浅拷贝一次,赋值给obj
2. object是可变对象,将会把object深拷贝一次,赋值给obj
如果obj是用strong修饰的,就没有拷贝一说了,将会直接把object赋值给obj

在内存计数方面
strong 会使object引用计数+1,obj的引用计数为1
copy   如果object是不可变对象,object引用计数+1,obj的引用计数为1
       如果object是可变对象,会将object深拷贝一份,object的引用计数不会变,obj的引用计数为1

综上所述,我们可以得出以下结论

  1. 当属性本身是可变对象时 此时只能用strong修饰,因为如下图,下图中,name属性经过setter时,得到的永远是不可变对象,当调用可变方法时,就会崩溃
  1. 当属性的赋值来源是可变对象时,如下图,看日志输出,发现当使用strong时,来源发生改变,属性值会跟着发生改变,当实用copy时,来源发生改变,属性不会跟着变
  1. 当属性的赋值来源是不可变对象时,如下图,发现strong和copy并没有什么区别

所以我们在选用修饰词时,我们要根据,属性本身是否可变,对属性赋值的来源是否可变,属性是否需要跟随来源的变化而变化等情况来选用属性的修饰词,不过,在实际开发中,大多数情况都是用copy

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2017.07.11 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档