美文网首页
.点语法和_下划线

.点语法和_下划线

作者: gpylove | 来源:发表于2018-11-02 16:04 被阅读11次

    点语法

            点语法是对属性的访问,经过oc消息派发,可以完成属性所定义的“内存管理语义”, 包含set和get方法。

    下划线

            下划线直接访问实例变量,不经消息派发访问速度更快,不会调用set和get方法,不会触发KVO。

    注意点

    1、懒加载,必须通过下划线来访问变量

    2、不要在init和dealloc中使用点语法

            对于 iOS 开发而言,直接使用成员变量效率会优于使用属性,但是直接使用成员变量也有不足之处:对于一个基本类型的变量(double, int)来说确实方便。但对于一个对象来说情况就复杂了,对象是 retain 呢还是 copy 呢?对于直接用成员变量来说,没有给出任何明确地行为,这往往会带来内存方面的问题。另外,如果这样直接的赋值,也不会触发 KVO。 

            使用点语法是更好的选择,因为这样可以兼容懒加载,同时也避免了使用下滑线的时候忽略了self这个指针,后者容易在block中造成循环引用,同时使用下划线是获取不到父类的属性,因为它只是对局部变量的访问。

            所以说我们应该结合起来去使用成员变量和点语法。对于基本数据类型,直接使用成员变量;对于一个 OC 对象,我们在只读操作的时候,直接使用成员变量即可。而在读写操作的时候,用点语法即可。这样一来既避免了内存问题,KVO问题,也尽可能的提高了效率。

    小知识:自动合成属性实例变量之后,@synthesize使用场景

    1.同时重写了 setter 和 getter 时

    2.重写了只读属性的 getter 时

    3.使用了 @dynamic 时

    4.在 @protocol 中定义的所有属性

    5.在 category 中定义的所有属性

    6.重载的属性

    小知识:懒加载

            懒加载,亦叫延迟加载,即在第一次需要的时候才去加载,本质上就是对一个实例的getter方法的重写。

    懒加载的优点

    相对来说,如果代码量不是很多,可读性略强;相对来说,防止为nil,减少了后续使用时安全检查的后顾之忧,使用适当,可节省内存资源。

    懒加载的缺点

    使用太泛滥,导致可读性变差,使用不得当,可能会造成死循环,导致crash,代码量增多。

    注意:在懒加载中,用下划线方法,避免死循环。

    后记:

    @property(copy,nonatomic) NSString *aCopyMStr;

    NSMutableString *mstrOrigin = [[NSMutableString alloc] initWithString:@"mstrOriginValue"];

     _aCopyMStr= mstrOrigin;

    NSLog(@"mstrOrigin输出:%p,%@\n", mstrOrigin,mstrOrigin);

    NSLog(@"aCopyMStr输出:%p,%@\n",_aCopyMStr,_aCopyMStr);

    NSLog(@"引用计数%@",[mstrOrigin valueForKey:@"retainCount"]);

    2018-11-06 15:21:46.407712+0800 OC-Swift[7127:192355] mstrOrigin输出:0x60000301e850,mstrOriginValue

    2018-11-06 15:21:46.407892+0800 OC-Swift[7127:192355] aCopyMStr输出:0x60000301e850,mstrOriginValue

    2018-11-06 15:21:46.408095+0800 OC-Swift[7127:192355] 引用计数2

    2018-11-06 15:27:50.202765+0800 OC-Swift[7169:194363] mstrOriginValueTest===mstrOriginValueTest

    @property(copy,nonatomic) NSString *aCopyMStr;

    NSMutableString *mstrOrigin = [[NSMutableString alloc] initWithString:@"mstrOriginValue"];

    self.aCopyMStr= mstrOrigin;

    NSLog(@"mstrOrigin输出:%p,%@\n", mstrOrigin,mstrOrigin);

    NSLog(@"aCopyMStr输出:%p,%@\n",self.aCopyMStr,self.aCopyMStr);

    NSLog(@"引用计数%@",[mstrOrigin valueForKey:@"retainCount"]);

    [mstrOrigin appendString:@"Test"];    NSLog(@"%@===%@",mstrOrigin,self.aCopyMStr);

    2018-11-06 15:22:07.847314+0800 OC-Swift[7127:192355] mstrOrigin输出:0x60000301e850,mstrOriginValue

    2018-11-06 15:22:07.847502+0800 OC-Swift[7127:192355] aCopyMStr输出:0x600003019920,mstrOriginValue

    2018-11-06 15:22:07.847629+0800 OC-Swift[7127:192355] 引用计数1

    2018-11-06 15:33:53.367396+0800 OC-Swift[7258:198057] mstrOriginValueTest===mstrOriginValue

            可见下划线只是访问实例变量,没有完成属性所定义的“内存管理语义”,这会带来内存方面的问题。当属性为copy时,需要用点语法调用属性才会对对象进行深拷贝,而下划线是指针指向相同的内存地址。

    相关文章

      网友评论

          本文标题:.点语法和_下划线

          本文链接:https://www.haomeiwen.com/subject/cidxxqtx.html