想知道以下代码中if (self = [super ...
的含义是什么?它试图防范什么情况?
- (id)initWithFrame:(CGRect)frame reuseIdentifier:(NSString *)reuseIdentifier {
if (self = [super initWithFrame:frame reuseIdentifier:reuseIdentifier]) {
// STUFF CONFIGURED HERE
}
return self;
}
采取from here。
答案 0 :(得分:5)
它正在防止超级实现返回nil。如果超类决定它无法初始化对象,它可能会释放它并返回nil,如果你试图进行任何初始化,那么会导致程序崩溃,因为你试图取消引用nil指针。
答案 1 :(得分:1)
如果超类中的函数失败并返回nil,那么“// STUFF CONFIGURED HERE”代码将不会执行,函数将返回nil。
这可能是你想要的行为,因为你的“// STUFF CONFIGURED HERE”代码可能依赖于超类函数来正常工作。
答案 2 :(得分:0)
super的初始化程序可以自由返回nil,也可以指向self之外的对象。这看起来很奇怪,但你不必看很远就能找到例子。考虑:
NSString *string1 = @"foo";
NSString *string2 = [[NSString alloc] initWithString:string1];
NSLog(@"\nstring1 is located at:%p \nstring2 is located at:%p", string1, string2);
显然,string1和string2是两个不同的对象,对吧?一个是常量字符串,另一个是在堆上的某处分配。所以看到这段代码的结果有点令人惊讶:
string1 is located at:0x3044
string2 is located at:0x3044
为什么两个指针都一样?好吧,NSStrings是不可改变的。由于它们无法改变,因此永远不会有两个具有完全相同值的理由。 NSString的-initWithString:方法如下:
-(NSString*)initWithString:(NSString*)string
{
if ([string isMemberOfClass:[NSString class]] == YES) {
[self release];
self = [string retain];
}
else {
// set up new immutable copy of string here
}
return self;
}
注意不寻常的'[自我释放]'。一个init方法将返回一个除了被分配的对象以外的对象,这是少数几个向自己发送-release有意义的情况之一。
还有其他情况,初始化程序可能决定返回一个不同的对象,或者nil,这就是为什么始终将super的初始化程序的结果赋给self的重要性。在访问其实例变量之前检查返回的指针是否为nil也很重要,这就是为什么赋值发生在'if'条件内。