处理NSError **指针的正确方法是什么?
- (BOOL)handleData:(NSDictionary *)data error:(NSError **)error {
// pass the error pointer to NSJSONSerialization
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:data options:options error:error];
// Check if NSJSONSerialization had errors
if (error) // <-- sometimes this works, sometimes it crashes...
return false;
...
return true;
}
- (void)someMethod {
NSError *error = nil;
BOOL result = [self handleData:dataDict error:&error];
if (error) {
// an error occurred
} else {
}
}
在此示例中,someMethod
将NSError
引用传递给handleData:error
。这是通过传递指针/地址而不是对象(...error:&error
)
然后方法handleData:error
将此指针传递给dataWithJSONObject:options:error
(现在没有&
)。现在,我想检查是否发生了错误,但是正确的方法是什么?
if (error)...
// This works if error == nil. However this is not always the case.
// Sometimes error is some address (e.g. 0x600001711f70) and *error == nil
// from the start of the method (passing error to NSJSONSerialization has no
// influence on this
if (*error)...
// This works in cases where error itself is not nil, but it crashes if
// error == nil
为什么在某些情况下是error == nil
而在其他情况下是error != nil
但为什么是*error == nil
?
在方法之间传递错误并检查是否发生错误的正确方法是什么?
答案 0 :(得分:2)
找到答案的地方是Introduction to Error Handling Programming Guide For Cocoa。约定为:
方法可以通过NSError
参数返回NSError **
对象,这样的方法还应该具有非void
返回类型,并通过其返回指示成功或失败值。因此,以您的示例为例,dataWithJSONObject:options:error:
在遇到错误时将返回nil
,并且可能通过其第三个参数返回错误对象。
任何接受NSError **
参数以返回错误的方法都应接受NSError *
变量或 NULL
的地址。后一个值表示用户不希望返回错误对象。这意味着接受NSError **
参数的方法必须在尝试通过它分配错误对象之前,必须检查参数值是否不是NULL
。
因此,您的方法handleData:error:
必须准备好接受NULL
并需要对其进行测试。因此,您的代码必须包含类似于以下内容的内容:
// Check if NSJSONSerialization had errors
if (jsonData == nil)
{
// Error occurred, did it return an error object?
if (error != NULL && *error != nil)
{
// we have an error object
}
else
{
// we have an error but no error object describing it
}
}
else
{
// no JSON error
}
HTH