self是一个隐藏的实例变量,指向当前对象:
- (id) initWithAmount:(double)theAmount forBudget:(Budget *)aBudget{
if(self = [super init]){
budget = aBudget;
amount = theAmount;
}
return self;
}
与
类似this.budget=super.aBudget;
this.amount=super.theAmount;
通常:
if(control)//true or false
{
//stmts will get executed
}
但不是在这里返回一个真值,而是指定了自己的超级。为什么会这样?
它与构造函数类似吗?如何在目标C中使用constructors(default,parameterised and copy)
?
答案 0 :(得分:4)
因为赋值表达式也返回赋值的结果,
if (self = [super init]) { ...
相当于:
self = [super init];
if (self) { ...
由于if
不仅测试纯布尔值,而且将非零,非NULL
或非 - nil
的所有内容视为真,if
在分配后self
为nil
的语句测试。
当我们编写自己的init
方法时,我们应该将[super init]
分配给self
,因为init
方法可以自由地返回与接收方不同的对象方法。如果我们刚刚调用[super init]
而未将其分配给self
,我们可能会初始化与self
不同的对象,这显然是不可取的。
答案 1 :(得分:4)
此表单只是以下代码的简写形式:
- (id)initWithAmount:(double)theAmount forBudget:(Budget *)aBudget {
self = [super init]; // you must do this, because every object inherits all properties
// from the parent class, and they must be initialized
// init can return nil if there was an error during the initialization
// so if the parents initialization failed, there is no point of initializing
// the child object
if (self != nil) {
budget = aBudget;
amount = theAmount;
}
return self;
}
答案 2 :(得分:1)
这是在Objective-C中定义初始化器的方式。它是两阶段创建模式的一部分:分离内存分配和对象的初始化。作为self引用初始化程序所在的对象实例,它必须向上继承树并设置它们返回自身的内容,之后轮到你了。
super的调用仅用于指定的初始值设定项。你可以有更多的初始化器,它应该总是使用指定的初始化器。
模式
- (id)init {
self = [super init];
if (self) {
// code
}
return self;
}
是处理故障的正确方法。如果self = [super init];
返回nil,测试将失败:继承树中的初始化程序中发生错误,因此您不希望使用失败的初始化并跳过自己的代码。