在类函数中使用 @synchronized(self) ...
Posted
技术标签:
【中文标题】在类函数中使用 @synchronized(self) ...【英文标题】:Using @synchronized(self) ... in class-function在类函数中使用 @synchronized(self) ... 【发布时间】:2012-03-22 13:54:53 【问题描述】:我无意中在类方法中使用了带有信号量 self
的 @synchronized
块。
+(void)someFunction
@synchronized(self)
/* some code */
这似乎是有效的代码,至少编译器没有给我任何不好的反馈。我的问题是:这里的self
是什么?据我所知,@synchronized
块不起作用,但它也没有崩溃。
我只是出于好奇。
【问题讨论】:
我曾经在我的博客here 中讨论过同样的事情。也许看看它。 【参考方案1】:self
在此实例中指的是类,而不是实例。在 ObjC 中,类本身就是对象。
【讨论】:
如果一个类是一个对象,它的实例是什么? 我认为它是“Class”类的一个实例。 [someNSObject 类] 记录为 +(Class)class 类对象是元类的一个实例,它是 ObjC 运行时自动创建的。类的“类方法”实际上只是元类上的实例方法,这就是类对象响应所有这些方法的原因。 传递给@synchronized指令的对象是用于区分受保护块的唯一标识符。如果您在两个不同的线程中执行上述方法,为每个线程上的 anObj 参数传递不同的对象,则每个线程都将获取其锁定并继续处理而不会被另一个线程阻塞。但是,如果在两种情况下都传递相同的对象,则其中一个线程将首先获取锁,而另一个线程将阻塞,直到第一个线程完成临界区【参考方案2】:self
在这种情况下是类本身,在类函数中使用 @synchronized
非常好,因为它们也是 Objective-C 对象。
【讨论】:
所以它会像 [TheClass 类]?【参考方案3】:@synchronized
语法是互斥体实现的编译器扩展。我假设你理解what it does。编译器会将其翻译成其他内容,据说类似于critical section,因为它占用的 CPU 较少。需要跟踪锁。该实现将使用一个对象来记录锁的状态,以保持其完整性(即一个锁不应该被获取两次,或者解锁两次)。
在@synchronized(self)
中,对象不必是self
。它可以是任何objective-c 对象。请注意,单个 @synchronized
块通常什么都不做(当您提到它不起作用时,它实际上表现正确)。但是当同一个对象上有两个@synchronized
块时,只会同时执行一个块,另一个块必须等待锁被解锁(即第一个块完成)。这有助于在多线程环境中保持同步。
【讨论】:
在这种语法上查看 ObjC docs 似乎比 Java 文档更有用。【参考方案4】:在类方法中self
是调用该方法的类。例如,您可以使用self
调用同一类的其他类方法。 [MyClass someFunction]
和 [self someFunction]
将等效于递归调用 someFunction
。我确信@synchronized
块按预期工作。
【讨论】:
以上是关于在类函数中使用 @synchronized(self) ...的主要内容,如果未能解决你的问题,请参考以下文章