Property attributes 属性的修饰符

属性到另一个难点就是它有很多的修饰符。

(译者注:这个地方其实用中文讲是很麻烦的一件事情……这两个词都有「属性」的意思。然而 property 其实最原始的意思是「私有财产」了,就是我们在类里面定义的一些东西,当它还没有被暴露在外部的时候,它是这个类的私有物。而 attribute 更偏向某些东西特有的一些性质,更接近「特征」的涵义,而直观从代码看,这一部分讲的内容更贴近「修饰符」。)

这些修饰符是在编译器里自动生成的,而且种类繁多,我们并不会在这里用到所有的属性,但是我们必须要了解他们。在属性被创建出来的时候,是有默认修饰符的,但我们必须根据不同的使用情境做调整。根据我的经验很多人会直接用默认的属性,这样其实是不好的。

属性一共有 11 种修饰符,它们会随机排列组合。这里我把这 11 种修饰符都介绍一下。下面的分类方式其实不是很科学,因为是按照我主观判断的使用频率来排序的:

  • strong: 属性的默认特征,也就是强引用,表示「储存在内存里」。
  • weak: 弱引用,用于避免循环引用。
  • copy: 拷贝,当属性有对象的时候,自动复制。
  • assign: 用来修饰基本数据类型,确保把值给了实例变量。
  • nonatomic: 原子性(atomic)属性,是指在多线程运行的时候,某一线程访问存或者取方法,其他线程不可以进入该存、取方法。非原子性(non-atomic)则相反,你要保证没有同时存取。
  • retain: strong 的旧格式,如果你看到了这个修饰符,说明真的接手了一个超级老的项目。
  • readonly: 只读,不能使用 setter 访问器。
  • readwrite: 读写,所有属性的默认特征,可以使用 getter 和 setter 访问器。
  • atomic: 看上面的 nonatomic,atomic 让代码更安全,也是所有属性的默认特征,会降低性能。
  • getter=: 改变 getter 访问器的名称。
  • setter=: 改变 setter 访问器的名称。

有一些修饰符明显是成组出现的,也就是说,在这些特征里面里面,你只能挑选一个,比如说 strong, weak, copy, assign 和 retain,readonly 和 readwrite,atomic 和 nonatomic。

有一些还是要解释一下。比如我们什么时候是 copy 而不用 strong?假设你创建了一个 NSMutableString 并把它的两个实例都声明为 strong,它们都可以指向同一个可变化的字符串,如果一个发生变化了,它们就都会发生变化。但是如果你想达到的效果是,把它们放进在数组里,它们在数组内部发生变化,但是它本身不变,那这个时候你就要用到 copy 了。

getter= 和 setter= 允许你改变 getter 和 setter 访问器的名称,但是当你在使用点运算符的时候,它们就不管用了。苹果经常在布尔值属性前面,用到 "is" 这个前缀,这个时候就要用到 getter= 和 setter= 了,通过自定义 self.view.userInteractionEnabled 就会变成 [self.view isUserInteractionEnabled]。

现在我们来这么定义 name 属性:

@property NSString *name;

在这里我们没有手动写任何的修饰符,都是默认的设定,我们把默认设定写出来:

@property (strong, atomic, readwrite) NSString *name;

在之前有个例子,就是可以用 NSMutableString 来代替NSString,也就是说,字符串完全有可能被人偷偷修改。所以你想保护你的数据的时候,应该用 copy 来代替 strong,就像这样:

@property (copy, atomic, readwrite) NSString *name;

在这种情况下,atomic 和 readwrite 都是默认的设定,可以不用写出来,代码就可以简化成这样子:

@property (copy) NSString *name;

所以你只需要修改你需要的修饰符就好啦~

results matching ""

    No results matching ""