-1

全部。我有一个方法:

-(void)connectToServer:(NSError**)error{
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
         //bla bla bla code;
         *error=[NSError bla bla bla];
    }
}

但是在那个错误变量之后没有修改。它没有块变量。我如何修改此方法以将 (NSError**) 错误标记为 __block 变量。如果 __block 变量仅用于局部变量?

现在我用 __block 属性解决了组织局部变量的问题:

-(void)connectToServer:(NSError**)error{
    __block NSError *localError=*error;
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
         //bla bla bla code;
         localError=[NSError bla bla bla];
    }
    *error=localError;
}

但是这个解决方案不像我的,因为我需要重新声明 __block NSError *localError=*error;

4

2 回答 2

3

要从块内进行修改error,您不需要局部__block范围变量。直接分配*error = [NSError bla];已经可以了。

这是有效的,因为error它被本地范围内的块捕获。虽然error无法修改,但可以将其取消引用到NSError *x存储某些内容的地址,并且x确实可以在块内进行更改。

但是,您需要绝对确定NSError *x所引用的任何变量error都足够持久。

于 2013-02-04T06:47:22.663 回答
2

亩。

你在做什么没有多大意义。该connectToServer:方法很可能会在该块设置error变量之前返回,这意味着调用者不会看到有效的对象。

您需要让块调用另一个方法来处理导致的任何错误,或者同步运行块,以便connectToServer:在块完成之前不会返回。

此外,在第二种情况下,您应该遵循Cocoa 的错误处理约定,并通过直接返回该方法来指示发生了错误。

这应该重写为:

- (void)connectToServer
{
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        //bla bla bla code including error generation
        dispatch_sync(/* Get appropriate queue; probably main */, ^{
            // Handle error somehow
        });
    });
}

或者:

- (BOOL)connectToServer: (NSError **)e
{
    __block BOOL success = NO;
    // Note: dispatch_sync()
    dispatch_sync(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{
        //bla bla bla code;
        success = /* Get success value */;
        *e = /* Get error */;
    });
    return success;
}
于 2013-02-04T06:04:51.263 回答