Что означает isConcurrent для NSOperation, запущенной из NSOperationQueue?
Потому что NSOperationQueue
всегда запускает задачи в новом потоке,
Меня смущает роль isConcurrent
, Когда NSOperation
бежит от NSOperationQueue
.
Если у меня есть два подкласса NSOperation
, оба выполняющих асинхронные процессы, оба запускаются из NSOperationQueue
и в обоих я переопределяю isCancelled
, isExecuting
, isFinished
и isReady
.
Какая будет разница, если в одном я переопределяю isConcurrent
Всегда return YES
, а в другом всегда return NO
.
Кто на самом деле звонит isConcurrent
? Как меняется логика, если она NO
или YES
.
3 ответа:
Это устаревший метод, используемый до OS X v10. 6 и до iOS 4, то есть до введения GCD для
NSOperationQueue
диспетчеризации.Из doc
Операционные очереди обычно предоставляют потоки, используемые для выполнения их операций. В OS X v10.6 и более поздних версиях очереди операций используют библиотеку
libdispatch
(также известную как Grand Central Dispatch) для инициализации выполнения своих операций. В результате операции всегда выполняются в отдельном потоке , независимо от обозначаются ли они как параллельные или не-параллельные операции. в OS X v10. 5, однако, операции выполняются на отдельных потоках только в том случае, если их методisConcurrent
возвращаетNO
. Если этот метод возвращает значение YES, ожидается, что объект operation создаст свой собственный поток (или запустит некоторую асинхронную операцию); очередь не предоставляет для него поток.Если вы используете OS X >= 10.6 или iOS >= 4, Вы можете спокойно игнорировать его.
Как подтверждение этого факта, от Дока оф
isConcurrent
В OS X v10.6 и более поздних версиях очереди операций игнорируют значение, возвращаемое этим методом, и всегда запускают операции в отдельном потоке.
Теперь я добавил более краткий ответ, оставив это на некоторое время, поскольку это было частью обсуждения...
Хорошо, я был вполне доволен своим использованием методаisConcurrent
до сегодняшнего дня !Я прочитал предложение:
В OS X v10.6 и более поздних версиях очереди операций игнорируют значение, возвращаемое этот метод и всегда запускает операции на отдельном потоке.
В качестве предупреждения, относящегося к QA1712, указывая, что для параллельных операций
start
метод теперь может быть вызван в другом потоке, чем тот, который поставил операцию в очередь, что является изменением в 10.6 и iOS 4.Я не прочитал это как указание на то, что метод
isConcurrent
полностью игнорируется очередью и не имеет никакой цели вообще, просто он больше не влияет на поток, на которомstart
вызывается. Возможно, я неправильно понял это.Я также неправильно понял первоначальный вопрос как более общий о параллельных операциях и флаге
isConcurrent
, а также принятый ответьте так же эффективно, сказавФлаг
isConcurrent
можно игнорировать начиная с версии 10.6 и iOS 4Я не уверен, что это правильно.
Если я понимаю первоначальный вопрос сейчас, перефразируя:
Учитывая правильно построенный параллельный
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
, который управляетNSURLConnection
.NSURLConnection
имеет свой собственный механизм для работы в фоновом режиме, так что не нужно делать параллельныйNSOperationQueue
.NSOperationQueue
?- Это для того, чтобы операция могла извлекайте пользу из других особенностейNSOperationQueue
, таких как зависимости и т. д. Вводящая в заблуждение часть документации относится только к тому потоку, на котором вызывается методstart
NSOperation
. Это изменение вызвало проблему, обсуждавшуюся в QA1712.
Перефразируя первоначальный вопрос следующим образом:
При правильно построенном параллельном
NSOperation
действительно ли значение, возвращаемоеisConcurrent
, изменяет выполнение операции вообще?В то время как мы могли бы попытаться понять, как флаг
isConcurrent
используетсяNSOperation
,NSOperationQueue
, или другие части операционной системы, было бы ошибкой полагаться на любую информацию, которую мы обнаружили.Назначение флага описывается только следующим образом:
Верните YES, если операция выполняется асинхронно по отношению к текущему потоку или нет, если операция выполняется синхронно с любым потоком, который ее запустил.
Пока вы правильно отвечаете,не должно быть важно, кто вызывает метод или как он влияет на любую логику внутри рамок Apple.
Дополнительные Примечания:
В документации содержится ссылка на изменение способа использования этого значения
NSOperationQueue
до и после OSX 10.6 и iOS 4.0.Это изменение вызвало проблему, описанную вQA1712 . Этот комментарий обычно интерпретируется как подразумевающий, что флагВ OS X v10.6 очереди операций игнорируют значение, возвращаемое isConcurrent, и всегда вызывают метод start вашей операции из отдельного потока. Однако в OS X v10.5 очереди операций создают поток только в том случае, если isConcurrent возвращает значение NO. ...
isConcurrent
больше не используется после 10.6 и iOS 4 и может быть проигнорирован. Я с этим не согласен интерпретация как метод не была официально признана устаревшей и до сих пор документируется как обязательное переопределение для параллельных операций. Кроме того, тот факт, что его использование изменилось в прошлом, является напоминанием о том, что он может измениться снова в будущем, поэтому мы должны правильно реагировать, даже если мы подозреваем, что в настоящее время он не имеет никакого эффекта.