В приложении Какао Objective-C, которое я разрабатываю, у меня есть NSTableView с делегатом, который реализует tableViewSelectionDidChange. В реализации метода делегата я поместил фоновую последовательную очередь, реализованную с помощью GCD, которая обрабатывает загрузку выбранного в данный момент объекта в таблице, чтобы он отображался в подробном NSView, который находится справа от таблицы. Мое желаемое поведение состояло бы в том, что, если фоновая нить не закончилась и в левой таблице есть новый выбор, я хотел бы отменить его и начать новый поток для нового выбора. Я нашел очень элегантное решение с использованием GCD здесь , которое использует:
dispatch_block_cancel(work);
Проблема в том, что, как сказано в ссылке:
"Следует отметить, что dispatch_block_cancel не имеет преимущественного значения. Если рабочий блок находится в середине длительной операции, dispatch_block_cancel не будет принудительно завершать его. Для этого мы должны периодически проверять для отмены с dispatch_block_testcancel. Вот пример: "
for (...) {
/* do some work */
[NSThread sleepForTimeInterval:0.2];
if (dispatch_block_testcancel(work) != 0) {
/* exit gracefully */
return;
}
}
Проблема в том, что в моем приложении самая длинная операция, выполняемая в реализации tableViewSelectionDidChange, состоит из одной строки кода, и я не могу реорганизовать свой код, чтобы изменить это, потому что этот оператор вызывает внешнюю библиотеку, которую я использую. В этом случае я не могу проверить, отменен ли блок с помощью:
if (dispatch_block_testcancel(work) != 0) {
/* exit gracefully */
return;
}
потому что поток заблокирован из-за длительной однострочной операции. Можно ли надеяться, что кто-нибудь предложит какую-то стратегию, желательно с использованием GCD? Я знаю о NSOperation и NSOperationQueue, но прежде чем научиться их использовать, я хотел бы убедиться, что у них нет проблем с отменой операций в середине 1-строчного оператора, как, очевидно, делает GCD. Большое спасибо за любую помощь.