Операция не отменена должным образом - PullRequest
0 голосов
/ 10 августа 2011

Я использую NSOperation для выполнения тяжелого анализа данных, а затем возвращаюсь обратно в основной поток с объектами, готовыми для использования моим приложением.Я обрабатываю все операции, помещая их в одиночную NSOperationQueue.Я делаю это, чтобы контролировать, сколько обработки происходит в любой момент, потому что каждая операция временно использует довольно большой объем памяти.

Итак, у меня есть сценарий, в котором у меня может быть несколько контроллеров представления на экране.Каждый контроллер представления создаст операцию синтаксического анализа при загрузке и добавит ее в очередь.Я разрешаю 2 одновременные операции обработки, установив maxConcurrentOperationCount.Каждый контроллер представления создает операцию обработки, помещает ее в одноэлементную очередь и сохраняет операцию в качестве свойства, поэтому у него есть дескриптор.

Если контроллер представления должен уйти в ответ на инициированный пользователемУдалить действие. Я использую свойство NSOperation в методе dealloc моего контроллера представления, чтобы отменить операцию:

-(void)dealloc{
    [self.currentOperation cancel];
    [super dealloc];
}

В моем подклассе NSOperation я проверяю свойство isCancelled в нескольких местах (в основном перед значительными частямивыполняется работа) свойство isCancelled и попытка ответить на него:

if([self isCancelled]){
    // Perform cleanup
    return;
}

Проблема заключается в том, что свойство isCancelled оценивается как ложное, и операция продолжается, в конечном итоге вызывая Core Data, чтобы попытаться получить данные, которые имеютбыл удаленЯ вижу, что это происходит, даже когда я размещаю проверку isCancelled непосредственно перед запросом на выборку Core Data.

У меня есть обходной путь, чтобы предотвратить сбой приложения, но я думаю, что могу ошибаться в реализации.Есть ли другой способ сохранить дескриптор операции во время ее обработки, чтобы я мог отменить ее при необходимости?Мой метод не сохраняет правильную ручку операции и не позволяет ее отменить должным образом?

1 Ответ

2 голосов
/ 10 августа 2011

Вы не можете делать логику подобным образом в dealloc.

Во-первых, dealloc должен вызывать в последнем случае суперлоцклок.Как только это будет сделано, объект исчезнет, ​​и все последующее поведение при обмене сообщениями не будет определено (произойдет сбой).

Также очень вероятно, что очередь сохранит операцию, таким образом делая отмену в dealloc бессмысленной, поскольку dealloc не может бытьвызывается до тех пор, пока очередь не освободится (если только управление вашей памятью не испорчено).

Вам необходимо полностью отделить логику отмены / аннулирования от управления памятью.

...