如果[super init]返回nil,为什么不抛出异常?

时间:2011-07-04 18:27:39

标签: objective-c cocoa-touch exception init

这被认为是典型的

- (id)init {
    self = [super init];
    if (self) {
        // <#initializations#>
    }
    return self;
}

但是,选择这样一些实际上做出适当反应的东西不是更好吗?

- (id)init {
    self = [super init];
    if (self) {
        // <#initializations#>
    } else {
       @throw [NSException exceptionWithName:NSInternalInconsistencyException reason:@"you think your constructor is executing, but it's not"] userInfo:nil]
    }
    return self;
}


这个问题的推论是,“在[super init]返回nil的情况下,你应该在init方法中处理这个问题吗?

4 个答案:

答案 0 :(得分:10)

不,Objective-C中的异常是指您无法真正恢复的状态,而不仅仅是表明操作失败的状态。如果初始化程序失败,只需返回nil即可显示它。

答案 1 :(得分:10)

不是真的。

使用:

self = [super init];

你正在调用你的超类init方法,只有在RARE情况下才会返回nil。 (如果系统内存不足,你还有其他问题)。

if(self)

如果没有返回实例(它为零),则不会通过,因此不需要else。

旧的方式是

if((self = [super init))
{
    // do initialization
}
return self

编辑:正在阅读Cocoa Fundementals指南并在错误处理下找到了这个:

  

如果在方法中遇到错误   实现是一个系统级别或   Objective - C运行时错误,创建和   如有必要,提出例外,并且   如果可能的话,在本地处理它。在   可可,通常是例外   保留用于编程或意外   运行时错误,例如越界   集合访问,试图变异   不可变对象,发送无效   消息,并失去连接   窗口服务器。你经常服用   通过例外处理这些错误   在创建应用程序时   而不是在运行时。可可   预定义了几个例外   可以捕获异常处理程序。   有关预定义的信息   例外和程序和API   用于提出和处理异常,   请参阅异常编程主题。

     

对于其他类型的错误,包括   预期的运行时错误,返回nil,   NO,NULL或其他类型 - 适合   调用者的形式为零。例子   这些错误包括无能   读取或写入文件,失败   初始化一个对象,无法做到   建立网络连接,或者   无法在中查找对象   采集。如果使用NSError对象   你觉得有必要回来   有关的补充信息   发件人的错误。一个NSError对象   封装有关的信息   错误,包括错误代码(哪个   可以特定于Mach,POSIX或   OSStatus域名)和字典   程序特定信息。该   负值是直接的   返回(零,否,依此类推)应该   是错误的主要指标;   如果你确实沟通更具体   错误信息,返回NSError   对象的间接参数   方法。

答案 2 :(得分:6)

一个原因,为什么你应该这样做,JustSid说的是:

在面向对象的设计中,您应始终编写代码,就好像您可能会将您的课程交给另一个开发人员的另一个项目。所以你不能假设,他的项目初始化失败可能和你的项目一样糟糕。也许这个开发人员是你5年。想象一下,你想要重用你的麻烦来修复你的200课程。

答案 3 :(得分:3)

返回nil是合适的事情。将任何消息发送到nil的部分原因是允许并定义为返回nil,因此您可以构建复合语句,如:

resultObject = [[[[class alloc] init] autorelease] someProperty];

即使任何单个方法调用返回nil,该语句也会一直执行。为了适应它,init约定是在超类这样做的情况下返回nil。

正如JustSid指出的那样,ObjC仅对不可恢复的问题使用例外。