" addDependency"在iOS中无法正常工作

时间:2016-09-29 19:06:31

标签: ios objective-c nsoperationqueue

我有两个NSOperation个对象" A"和" B",并希望使用依赖,因为我需要让完整的" B"首先然后开始" A"。

- (void)viewDidLoad {
    [super viewDidLoad];

    NSOperationQueue *myQueue = [NSOperationQueue new];
    NSOperation *op1 = [[NSOperation alloc] init]; // Its a background(concurrent) thread.
    op1.completionBlock =^{
        NSLog(@"A");  
    };

    NSOperation *op2 = [[NSOperation alloc] init];  
    op2.completionBlock =^{

        NSLog(@"B");
    };
    [op1 addDependency:op2];
    [myQueue addOperation:op1];
    [myQueue addOperation:op2];
}

预期产出:

 B
 A

但有时候:

 A
 B

但是我想完成第一个B然后需要开始A.请帮助我。

3 个答案:

答案 0 :(得分:1)

  1. 首先创建操作op1
  2. 如果操作op2提供的数据不可用,请创建操作op2
  3. 使操作op1依赖于操作op2。即。像op1.addDependency(op2);
  4. 之类的东西

    或检查这个

    NSOperationQueue *queue = [[NSOperationQueue alloc] init];
    NSOperation *op1;
    NSOperation *op2;
    
    //... initialize op1 and op2 however you please ...
    
    [op1 setCompletionBlock:^{
            if ([op1 satisfiesSomeCriteria]) {
                [queue addOperation:op2];
            }
     }];
    [queue addOperation:op1];
    

答案 1 :(得分:1)

这里,完成块不是队列的一部分,而是在另一个线程上的Operation Queue之外运行。因此,操作A的completionBlock将与操作B同时运行。

根据您的问题,您正在使用completionBlocks将操作A中的信息传递给B.

以下是一些解决方案:

  • 为所有A(不弱)提供B引用,因此当B运行时,它可以从操作A中选择结果。

  • 保持所有A操作直到B运行,然后重新创建完成块作为另一个NSOperation,请参阅下面的代码:

NSOperation *operA = [NSBlockOperation blockOperationWithBlock:^{ // do stuff 
}]; 

NSOperation *operationATail = [NSBlockOperation blockOperationWithBlock:^{ // do completionBlock stuff
}]; 

// First bullet point
[operationATail addDependency:operA];

// Second bullet point
[operationB addDependency:operationATail]; 

[self.queue addOperations:@[operA, operationATail, operationB] waitUntilFinished:NO];

答案 2 :(得分:0)

我可以使用NSBlockOperation类代替NSOperation来实现它。这是一个示例代码段。

    NSOperationQueue *myQueue = [NSOperationQueue new];
    NSBlockOperation *blockOp1 = [[NSBlockOperation alloc] init];
    [blockOp1 addExecutionBlock:^{

        NSLog(@"1");
    }];

    NSBlockOperation *blockOp2 = [[NSBlockOperation alloc] init];
    [blockOp2 addExecutionBlock:^{

    NSLog(@"2");
    }];

    [blockOp1 addDependency:blockOp2];
    [myQueue addOperation:blockOp1];
    [myQueue addOperation:blockOp2];

   Output: 2
           1