如何在块上使用停止条件,如NSDictionary类中的enumerateObjectsUsingBlock?

Ale*_*lla 7 objective-c pass-by-reference objective-c-blocks

我想打一个方法上我的课像enumerateObjectsUsingBlock:^(id obj, NSUInteger idx, BOOL *stop)NSDictionary类.

我对块的使用有一点了解,但是我还没弄清楚如何使enumerateObjectsUsingBlock函数使用的停止条件.有什么建议?

bbu*_*bum 13

stop标志用于这样的:

[coll enumerateUsingBlock:^(id o, NSUInteger i, BOOL *stop) {
      if (... check for stop ... ) {
           *stop = YES;
           return;
      }
 }];
Run Code Online (Sandbox Code Playgroud)

枚举块返回时,集合检查*stop.如果是YES,它将停止枚举.

它以这种方式实现,而不是返回值,因为这允许并发枚举而不检查块的返回值(这会产生开销).即在并发枚举中,集合可以进行dispatch_async()任意数量的同时迭代并定期检查*stop.无论何时*stop转换到YES,它都会停止调度更多的块(这也是为什么stop标志不是硬停止的原因;一些未指定的迭代次数可能仍在进行中).

在你的迭代器中,你可能会:

 BOOL stop = NO;
 for(...) {
     enumerationBlock(someObj, someIndex, &stop);
     if (stop) break;
 }
Run Code Online (Sandbox Code Playgroud)


Gab*_*lla 6

下面的代码定义了一个方法,该方法将块作为参数并一直执行它,直到由块shouldStop设置为止NO.

- (void)myMethod:(void(^)(BOOL *stop))aBlock {
    BOOL shouldStop = NO;
    while (!shouldStop) {
        aBlock(&shouldStop);
    }
}
Run Code Online (Sandbox Code Playgroud)

解释相当简单.块是一个带有一些参数的函数.在这种情况下,我们将指向BOOL我们拥有的变量的指针作为参数传递.通过这样做,我们允许块设置该变量 - 在这种情况下 - 指示循环应该停止.

在这一点上,通过的块可以做类似的事情

[self myMethod:^(BOOL *stop) {
      if (arc4random_uniform(1)) {
          *stop = YES;
      }
}];
Run Code Online (Sandbox Code Playgroud)