Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I cancel an NSOperation's dependencies?

I have some NSOperations in a dependency graph:

NSOperation *op1 = ...;
NSOperation *op2 = ...;

[op2 addDependency:op1];

Here's how I'm running them:

NSOperationQueue *queue = [[NSOperationQueue alloc] init];
[queue addOperation:op1];
[queue addOperation:op2];

Now I need to cancel them. How do I ensure that all the NSOperations in a dependency graph are cancelled, and that no other NSOperations are cancelled?


what I've tried:

Calling cancel on either NSOperation doesn't cancel the other (as far as I can tell):

[op1 cancel]; // doesn't cancel op2
// -- or --
[op2 cancel]; // doesn't cancel op1

Cancelling the queue would also cancel operations that aren't part of the dependency graph of op1 and op2 (if there are any such operations in the queue):

[queue cancelAllOperations];

So I solved this using a custom method that recursively looks through an NSOperation's dependencies and cancels them. However, I'm not happy with this solution because I feel like I'm fighting the framework:

- (void)recursiveCancel:(NSOperation *)op
{
    [op cancel];
    for (NSOperation *dep in op.dependencies)
    {
        [self recursiveCancel:op];
    }
}
like image 480
Matt Fenwick Avatar asked Jan 21 '15 14:01

Matt Fenwick


People also ask

How do I cancel NSOperation?

you use cancel , and test whether self (the NSOperation ) has been cancelled during execution.

How do I cancel a queue in Swift?

If you just want to cancel a specific Operation , then you can call the cancel method. If, on the other hand, you wish to cancel all operations that are in an operation queue, then you should call the cancelAllOperations method defined on OperationQueue .

Is NSOperation thread safe?

You can safely use a single NSOperationQueue object from multiple threads without creating additional locks to synchronize access to that object. Operation queues use the Dispatch framework to initiate the execution of their operations.

What are NS operations?

An abstract class that represents the code and data associated with a single task.


1 Answers

Sounds to me like you are trying to group operations together in the same queue. To achieve that it's best to split them up using a queue per group. So for each group create an NSOperation subclass in concurrent mode, include a queue, add each sub-operation to the queue. Override cancel and call [super cancel] then [self.queue cancelAllOperations].

A huge advantage of this approach is you can retry operations by adding again to the sub-queue, without affecting the order of the main queue.

like image 55
malhal Avatar answered Oct 02 '22 02:10

malhal