我正在从我的控制器调用一个异步函数,并将一个对错误变量的引用传递给它,比如说:
NSError *err=nil;
[self myAsyncTask:&err];
如果控制器被释放,则 err 变量不再存在,因此应用程序崩溃并出现 BAD_ACCESS 错误(因为函数尝试更改 err 变量的值)。我该如何处理?
我正在从我的控制器调用一个异步函数,并将一个对错误变量的引用传递给它,比如说:
NSError *err=nil;
[self myAsyncTask:&err];
如果控制器被释放,则 err 变量不再存在,因此应用程序崩溃并出现 BAD_ACCESS 错误(因为函数尝试更改 err 变量的值)。我该如何处理?
请注意,没有一个内置框架方法使用通过引用传递错误报告和异步调用——它们都使用委托或块来传达错误状态。使用块,您的 API 可以被编写成如下使用:
[self doAsyncTaskWithErrorHandler: ^(NSError *error) {
//Handle error
}];
方法签名可能看起来像
- (void)doAsyncTaskWithErrorHandler:(void (^)(NSError *error))errorHandler;
在实现中,您曾经*error = someError;
做过类似的事情:
NSError *error = ...;
if (errorHandler) {
errorHandler(error);
}
如果我没记错的话,这并不是对象生命周期的真正问题——如果在设置错误之前弹出堆栈帧,那么问题中的模式也可能会导致崩溃。
我该如何处理?
如果您正在处理异步函数,则必须确保它使用的任何变量在该函数完成之前保持有效。Objective-C 的内存管理非常适合这一点——像你这样的方法-myAsyncTask
可以保留它的参数,直到它不再需要它们。这样,即使控制器(用你的话)被释放,变量引用的对象将保持有效。
另一种方法是使用块来实现异步功能。块会自动保留它们使用的资源,因此它们可以有效地为您解决这个问题。