原子和非原子属性之间有什么区别? [英] What's the difference between the atomic and nonatomic attributes?
问题描述
atomic
和 nonatomic
在财产声明中的含义是什么?
What do atomic
and nonatomic
mean in property declarations?
@property(nonatomic, retain) UITextField *userName;
@property(atomic, retain) UITextField *userName;
@property(retain) UITextField *userName;
这三者之间的操作差异是什么?
What is the operational difference between these three?
推荐答案
最后两个是相同的; atomic是默认行为(请注意,它实际上不是关键字;仅通过缺少 - <$来指定在最新版本的llvm / clang中添加了c $ c> atomic 作为关键字。 nonatomic
The last two are identical; "atomic" is the default behavior (note that it is not actually a keyword; it is specified only by the absence of -- nonatomic
atomic
was added as a keyword in recent versions of llvm/clang).
假设您正在@synthesizing方法实现,原子与非原子改变生成的代码。如果您正在编写自己的setter / getter,则atomic / nonatomic / retain / assign / copy仅仅是建议性的。 (注意:@synthesize现在是最近版本的LLVM中的默认行为。也没有必要声明实例变量;它们也将自动合成,并且将具有 _
在其名称前添加以防止意外直接访问)。
Assuming that you are @synthesizing the method implementations, atomic vs. non-atomic changes the generated code. If you are writing your own setter/getters, atomic/nonatomic/retain/assign/copy are merely advisory. (Note: @synthesize is now the default behavior in recent versions of LLVM. There is also no need to declare instance variables; they will be synthesized automatically, too, and will have an _
prepended to their name to prevent accidental direct access).
使用atomic,合成的setter / getter将确保整个无论任何其他线程上的setter活动如何,值始终从getter返回或由setter设置。也就是说,如果线程A位于getter的中间,而线程B调用setter,则实际可行的值 - 一个自动释放的对象,很可能 - 将返回给A中的调用者。
With "atomic", the synthesized setter/getter will ensure that a whole value is always returned from the getter or set by the setter, regardless of setter activity on any other thread. That is, if thread A is in the middle of the getter while thread B calls the setter, an actual viable value -- an autoreleased object, most likely -- will be returned to the caller in A.
在非原子
中,不做任何此类保证。因此,非原子
比原子快得多。
In nonatomic
, no such guarantees are made. Thus, nonatomic
is considerably faster than "atomic".
What "atomic" does not do is make any guarantees about thread safety. If thread A is calling the getter simultaneously with thread B and C calling the setter with different values, thread A may get any one of the three values returned -- the one prior to any setters being called or either of the values passed into the setters in B and C. Likewise, the object may end up with the value from B or C, no way to tell.
确保数据完整性 - 主要挑战之一多线程编程 - 通过其他方式实现。
Ensuring data integrity -- one of the primary challenges of multi-threaded programming -- is achieved by other means.
添加到:
<$ c单个属性的$ c> atomicity 在多个依赖属性发挥作用时也无法保证线程安全。
atomicity
of a single property also cannot guarantee thread safety when multiple dependent properties are in play.
考虑:
@property(atomic, copy) NSString *firstName;
@property(atomic, copy) NSString *lastName;
@property(readonly, atomic, copy) NSString *fullName;
在这种情况下,线程A可以通过调用 setFirstName重命名对象:
然后调用 setLastName:
。在此期间,线程B可以在线程A的两个调用之间调用 fullName
,并将接收与旧姓氏一起使用的新名字。
In this case, thread A could be renaming the object by calling setFirstName:
and then calling setLastName:
. In the meantime, thread B may call fullName
in between thread A's two calls and will receive the new first name coupled with the old last name.
要解决此问题,您需要交易模型。即一些其他类型的同步和/或排除,允许在更新依赖属性时排除对 fullName
的访问。
To address this, you need a transactional model. I.e. some other kind of synchronization and/or exclusion that allows one to exclude access to fullName
while the dependent properties are being updated.
这篇关于原子和非原子属性之间有什么区别?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!