Objective C 中 Property的各种修饰词

Objective C 中 Property的各种修饰词

我们在定义perperty的时候都要指定修饰词,比如

atomic, copy, strong, weak等等,那么这些都是做什么用的?下面就所有修饰词作一说明。

Objective C中所有的修饰词有6对,12个,为什么用“对“这个词呢,因为它们每2个都是相对的,

atomic —- nonatomic

strong —– weak

readwrite —- readonly

getter= —- setter=

copy — assign

retain —- unsafe_unretained

 

atomic

(Properties are atomic by default, so if you don’t write nonatomic, it will be atomic (whether you write it or not). Atomic basically ensures that data is written or read atomically. So if thread A is still in the getter when thread B calls the setter, thread A will get a viable value. It is not necessarily thread-safe, but much safer than nonatomic. The problem with atomic though, is that it is quite slow compared to its opposite. Also, you must either implement both the setter and the getter, or neither. You cannot have a custom getter and a synthesized setter in an atomic property.)

Propteries默认是原子性的,因此如果你没有制定非原子性(使用修饰词 nonatomic),它就是具有原子性的。原子修饰词保证数据的读写是原子性的。比如线程A正在使用setter读取一个数据,而线程B正在使用setter修改这个数据,那么A就得到一个有效的值。它不是完全线程安全的,但是要比nonatomic安全。Atomic的问题是速度要比nonatomic慢。另外你要么都显示的实现setter和getter,或者都不实现(使用默认的),不可以只实现一个。

nonatomic

(This makes no such guarantees about atomicity (which is quite a cool word) as nonatomic. If thread A is in the middle of a getter for a nonatomic NSString, and Thread B tries to set it to “Microwave”, and Thread C tries to set it to “Refrigerator”, you might get “Microgerator”, or it may just be completely unreadable and crash the program. You never know, so if you use nonatomic, you must implement your own thread safety and atomicity. You will more often use nonatomic properties though, because they are FAST when compared to atomic ones.)

这个不保证数据的原子性。如果线程A正在访问一个nonatomic修饰的NSString的变量,同时线程B试图把他改成“Micrsowave“, 并且线程C试图改成“Refrigerator“,你或许得到”Micsogerator“,或者完全是不可读的或者使整个程序崩溃。你也许从来不知道,如果你使用nonatomic,你必须实现你自己的线程安全和原子性。不过你可能更多的使用的nonatomic,因为相比于atomic,它要更快。

strong

(This is also a default attribute, and must be overridden if you want to change it. In ARC, its opposite is the “weak” attribute. I started post-ARC, so my first-hand knowledge is better with strong and weak, compared to the pre-ARC ones listed later. Strong is generally used by a class to establish ownership of an object. It increases the retain count (something ARC deals with for you), it basically keeps the object that is pointed to in memory until that class instance stops pointing to it. This is usually what you want, but there it can cause something called a “retain cycle.” The weak attribute helps solve this issue.)

这个同样是默认是修饰词,而且必须被重载如果你要更改它(说的什么东东),在ARC的程序中,它所对应的是weak修饰词。我开始学objective c是在后ARC时代,因此我初期认识strong和weak,主要是后ARC的。Strong通常被用作类的变量,来表示一个对象所属关系。它会增加持有计数(有时候,ARC会帮你处理),基本上这个类会保持一个在内从里面的对象直到类实例不再指向它。通常这是这是你想要的,但是这同时也会造成 持有环问题,而weak就是来解决这个问题。

weak

(This gives a pointer to an object, but does not claim ownership, and does not increase the retain count. It basically keeps a valid pointer to an object as long as another class points to it strongly. If nothing else is trying to retain it, the weak pointer is automatically set to nil. An example where this would be useful is if you had two classes, one for a petOwner, and one for their pet. Lets say for some reason we want them to refer to each other, so you can request the pet of an owner, or an owner of a pet. If the pet’s petOwner property, and the petOwner’s pet property were both strong, the memory could never be released because they would both be telling ARC that they both need it. If we set the petOwner’s pet property to weak, then we avoid the retain cycle. If the pet object is destroyed, while the petOwner still has a reference to it, the petOwner’s pet property will be automatically set to nil.)

这个修饰词是表示这是指向一个对象的指针,但是它不拥有这个对象,它不会增加持有计数。它通常持有一个对象的指针只要另外一个类指向它(使用strong修饰词)。如果没有对象在持有这个它,这个weak的指针就会被自动设置成空(nil)。举个weak有用的例子,加入你有2个类,一个是PetOwner,另外一个是pet,你想让他们相互引用,然后可以通过petowner找到pet,也可以通过pet找到petowner。如果pet的petOwner属性和petOwner的pet属性都是strong,内存将永远不会被释放,因为它们都告诉ARC它们需要它。但是如果设置petOwner的pet属性为weak,那么我们可以避免这种持有环。如果pet对象被销毁,那么petOwner所持有的pet的指针会被自动设置为空(nil)

readwrite

(This is a default attribute and it can be overridden by readonly. This basically tells the compiler to generate both a getter and a setter (or an accessor and mutator if you want to use fancy language).

这个默认的修饰词,可以被readonly重载。这个修饰词告诉编译器为我们生成getter和setter

readonly

(This can override readwrite. It tells the compiler to only generate a getter for an object. One common thing to do with these two, is if you want a property visible to another class, but not able to be changed by an external class, set the property to readonly in your header file, and in your implementation file ( .m file), declare it as readwrite. That way your implementation has a getter and a setter, while external classes only get the getter.)

这个可以重写readwrite修饰词。这个修饰词告诉编译器只生成getter。利用readwrite和readonly这2个关键词,通常会被这样用,你希望某个类的属性对另外一个类是可见的,但是不可以被更改,因此你会在这个类的头文件中将这个属性设置成readonly,然后在实现文件中将他申明为readwrite,这样你的实现文件就有了getter和setter,但是对其他类来说只有getter。

getter=

(This just gives a custom name for a getter. The default getter is just the name of the property. For instance for the UISwitch control in iOS, the property that says whether the switch is on is just named “on”. To make things a bit more readable, they set this attribute to “getter=isOn”. That way you can do something like this:


if(someSwitch.isOn)

The getter= attribute is used purely for convenience or readability.)

这是getter方法的自定义名字。默认的getter其实就是属性的名字。例如,iOS的UISwitch控件,用来表示开关是否是on的属性就被命名为“on”。为了提高可读性,它们通常设置这个属性为

getter=isOn

这样定义之后,你可以下面的代码

if(someSwtich.isOn)

getter=修饰词纯属是为了方便和提高可读性。

setter=

(Similar to the getter=, it just gives a custom name to the setter. The default setter is just the capitalized property name with set as a prefix (so the default setter for “petOwner” is “setPetOwner”. This is again done purely for convenience or readability. I personally see this less often, but it is perfectly valid.)

copy

(I have not used this one much, but here is what I have learned. It is similar to strong, but instead of increasing the retain count and claiming ownership of an object, it copies the value of the object that it is assigned to, and takes strong ownership of that copy. The object must conform to the NSCopying protocol to allow this to work.)

我很少使用这个修饰词,下面是我所知道的。它非常类似于strong,但是它不会增加持有计数也不会声明对象拥有权,它只是拷贝对象的值,并且保持这个对象的强拥有权(我日,我翻译的这是什么东西,算了,就先这样)。不过对象一定遵守NSCopying协议。

assign

(A pre-ARC attribute. This is default behavior for primitive data types (like int, long, and float). It was used similar to “weak” for pre-ARC programs. It assumes the same ownership as “unsafe_unretained” mentioned below. It appears okay to use in an ARC project, but should be limited to properties for primitive types.)

这是ARC时代之前的修饰词,这个对与基本数据类型,如int,long,float,是默认的行为。在ARC时代之前,它和weak修饰词类似。它表明了和下面将要讲到的unsafe_unretained所定义的所属关系。似乎ARC程序中使用它是可以,不过仅限于基本数据类型的属性。

retain

(A pre-ARC attribute. This is the older version of strong. It claims ownership of the object and increases the retain count. You will have to manually release the object to decrease its retain count (which will release it from memory when the retain count goes to 0). You should not use this in an ARC project.)

这是ARC时代之前的修饰词。这是旧版的strong。它声明了对对象的所属权并且会增加持有计数。你必须手动释放对象来减少持有计数(当持有计数变成0的时候,这个占有的内存就会被释放掉)。你不应该在ARC的程序中使用它。

unsafe_unretained

(A pre-ARC attribute. This is similar to “weak”, but did not automatically set their value to nil if the referenced object was destroyed (as mentioned earlier). You should not use this in an ARC project.

这是ARC时代之前的修饰词,类似与weak,但是当引用对象被销毁的时候,系统不会自动设置它们的值为nil。你不应该在ARC的程序中使用它。

 

 

版权所有,禁止转载. 如需转载,请先征得博主的同意,并且表明文章出处,否则 按侵权处理.

    分享到:

留言

你的邮箱是保密的 必填的信息用*表示