从嵌套完成块返回值

时间:2018-10-09 16:03:54

标签: ios objective-c asynchronous objective-c-blocks

我有一个完成块,它带有一个根据用户选择是动态的参数,例如:

NSString *data = <some value based on user selection>;
[avc activity:data withBlock:^id _Nonnull{

}

此块的返回类型为id。

我还有另一个类似这样的块:

[self createItem:data completion:^(NSString * _Nullable item) {
    //value of item is received here
}];

我要实现的目标是:

NSString *data = <some value based on user selection>;
//This data is used in both the blocks
[avc activity:data withBlock:^id _Nonnull{
    [self createItem:data completion:^(NSString * _Nullable item) {
        return item; //Error here
    }];
}

由于内部块的返回类型为void,因此返回该项目将引发错误。我要实现的是,当内部块收到项中的值时,应将其返回给外部块。

我尝试使用这样的调度组:

NSString *data = <some value based on user selection>;
//This data is used in both the blocks
[avc activity:data withBlock:^id _Nonnull{
    __block NSString *url = nil;
    dispatch_group_t group = dispatch_group_create();
    dispatch_group_enter(group);
    [self createItem:data completion:^(NSString * _Nullable item) {
        url = item;
        dispatch_group_leave(group);
    }];
    dispatch_group_wait(group, DISPATCH_TIME_FOREVER);
    return url
}

这不起作用。等待语句后,该应用将无限期卡住。

有什么办法可以实现我正在尝试的东西?

1 个答案:

答案 0 :(得分:0)

[[NSOperationQueue new] addOperationWithBlock:^{
  NSString *data; // <some value based on user selection>;
  [avc activity:data withBlock:^id _Nonnull{
      __block NSString *url = nil;
      dispatch_semaphore_t finished = dispatch_semaphore_create(0);
      [[NSOperationQueue mainQueue] addOperationWithBlock:^{
        [self createItem:data completion:^(NSString * _Nullable item) {
            url = item;
            dispatch_semaphore_signal(finished);
        }];
      }];
      dispatch_semaphore_wait(finished, DISPATCH_TIME_FOREVER);
      return url
  }];
}];