因为NSOperationQueue
总是在新线程上运行任务,
当isConcurrent
从NSOperation
开始运行时,我对NSOperationQueue
的作用感到困惑。
如果我有两个NSOperation
子类,两个都运行异步进程,则都从NSOperationQueue
启动,并且我都覆盖isCancelled
,isExecuting
,{{1 }和isFinished
。
如果我在isReady
总是isConcurrent
而另一个总是return YES
,则会有什么不同。
谁实际致电return NO
?逻辑如果变为isConcurrent
或NO
。
答案 0 :(得分:5)
这是一种遗留方法,在OS X v10.6之前和iOS 4之前使用,即在NSOperationQueue
调度引入GCD之前使用。
来自doc
操作队列通常提供用于运行其操作的线程。在OS X v10.6及更高版本中,操作队列使用
libdispatch
库(也称为Grand Central Dispatch)来启动其操作的执行。因此,无论是将它们指定为并发还是非并发操作,操作始终在单独的线程上执行。 但是,在OS X v10.5中,仅当isConcurrent
方法返回NO
时,才会在单独的线程上执行操作。如果该方法返回YES,则操作对象应该创建自己的线程(或者启动一些异步操作);队列没有为它提供线程。
如果您运行的是OS X> = 10.6或iOS> = 4,则可以放心地忽略它。
作为对这一事实的证实,来自isConcurrent
在OS X v10.6及更高版本中,操作队列忽略此方法返回的值,并始终在单独的线程上启动操作。
答案 1 :(得分:2)
我现在添加了一个更简洁的答案,暂时离开了,因为它是讨论的一部分......
好的,直到今天我对使用isConcurrent
方法感到非常满意!
我读了这句话:
在OS X v10.6及更高版本中,操作队列忽略返回的值 这个方法总是在一个单独的线程上开始操作。
作为与QA1712相关的警告,指出对于并发操作,现在可以在与操作排队的线程不同的线程上调用start
方法,这是10.6和iOS 4中的更改。 / p>
我没有读到这一点,表明队列完全忽略了isConcurrent
方法,根本没有任何意图,只是它不再影响调用start
的线程。我可能误解了这个。
我也误解了原来的问题,作为关于并发操作和isConcurrent
标志的更一般的问题,并且接受的答案实际上是
自10.6和iOS 4
以来,isConcurrent
标志可以被忽略
我不确定这是否正确。
如果我现在理解原始问题,请解释:
鉴于正确构建的并发
NSOperation
,isConcurrent
标志本身是否实际上改变了操作的执行?
我想很难说所有可能的设置,但我们可以这样说:
它没有被弃用。 Apple批评方法是正常的 不再有用。
文档始终指的是必需的方法 覆盖。
或许isConcurrent
实际上已被弃用,但由于它只是一个BOOL
标志,因此在文档中弃用它可能不值得。或者它现在可能没有任何作用,但Apple已将其保留以备将来使用,并希望您按照描述覆盖它。
我创建了一个快速测试项目NSOperation
仅覆盖isConcurrent
和main
,isConcurrent
在任何阶段都未被调用。这是一个非常简单的测试。我猜你也可能测试过了吗?我想假设NSOperationQueue
没有调用NSOperation's
start
的默认实现。
那么我们离开了哪里?显然,实现它并返回YES
以满足记录的要求并不困难。然而,从我的角度来看,我认为从10.6和iOS 4.0的警告中说,现在可以安全地忽略它是太过分了。
我原来的答案......
isConcurrent
不是遗留方法,NSOperationQueue
不会忽略。其他答案中引用的文档有点不清楚,很容易被误解。
isConcurrent = YES
表示操作提供了自己的并发方法。或者换句话说,操作"isAlreadyConcurrent"
并且不需要NSOperationQueue
来提供和管理并发性。由于NSOperationQueue
不再提供并发性,因此需要在操作isFinished
或其isCancelled
(等)时告诉它,因此需要覆盖这些方法。
一个常见示例是管理NSOperation
的{{1}}。 NSURLConnection
拥有自己在后台运行的机制,因此不需要NSURLConnection
并发。
一个显而易见的问题是:“为什么将已经并发的操作放入NSOperationQueue
?”因此,操作可以受益于NSOperationQueue
类似依赖项等的其他功能。
文档中的误导性部分仅指的是调用NSOperationQueue
的{{1}}方法的线程。这一变化引发了QA1712中讨论的问题。
答案 2 :(得分:0)
将原始问题解释为:
如果正确构建并发
NSOperation
,isConcurrent
返回的值是否实际上会改变操作的执行?
虽然我们可以尝试了解isConcurrent
,NSOperation
或操作系统的其他部分如何使用NSOperationQueue
标志,但依赖任何信息都是错误的我们发现了。
该标志的目的仅描述为:
如果操作相对于当前线程异步运行,则返回YES;如果操作在启动它的任何线程上同步运行,则返回NO。
只要你正确回应,调用该方法或它如何影响Apple框架内的任何逻辑都不应该是重要的。
附加说明:
文档确实引用了NSOperationQueue
在OSX 10.6和iOS 4.0之前和之后使用此值的方式的更改。
在OS X v10.6中,操作队列忽略isConcurrent返回的值,并始终从单独的线程调用操作的start方法。但是,在OS X v10.5中,仅当isConcurrent返回NO时,操作队列才会创建一个线程。 ...
此更改导致QA1712中描述的问题。
此评论通常被解释为暗示在10.6和iOS 4之后不再使用isConcurrent
标志,并且可以忽略。我不同意这种解释,因为该方法尚未正式弃用,并且仍记录为并发操作的必需覆盖。
此外,它的使用在过去发生了变化,提醒人们将来可能会再次发生变化,因此即使我们怀疑它目前没有任何效果,我们也应该正确回应。