1

我试图重写init一个类的方法,以便初始化对象也初始化 ivar 对象:

-(id)init 
  {
    if (self = [super init])
    {
       someIVarObject = [SomeClass alloc] init];
    }
    return self;
  }

1)这个代码甚至可以工作,即便如此,这个解决方案是否不鼓励?
2)为什么if条件不是==?是任务吗?如果是这样,为什么if

对不起,如果这很明显!>_<

4

5 回答 5

3

是的,它会起作用,而且它仍然是它应该做的方式。

它所做的是调用[super init]并允许它做三件事之一;

  • 返回自我(即相同的对象self已经设置为。
  • 返回一个全新的对象。
  • 以失败告终nil

然后将结果分配给self,以确保构造函数的其余部分对正确的对象进行操作,以防它发生更改。if那里是为了捕捉返回 nil 的情况,[super init]在这种情况下应该跳过构造函数的其余部分。

于 2013-02-11T20:21:43.893 回答
2

1)在这里,您声明了一个局部变量someIVarObject。您应该在大括号中的类的接口或实现中声明它,然后将其分配为someIvarObject = .... 一个例子:

@implementation MyClass {
    SomeClass *someIvarObject;
}

- (id)init
{
    if(self = [super init])
    {
        someIvarObject = [[SomeClass alloc] init];
    }
    return self;
}

@end

2)这是一个任务。这个习语背后有很长的历史,但它主要归结为处理返回与最初调用[super init]不同的对象的可能性。init

于 2013-02-11T20:18:37.620 回答
2

这...

if(self = [super init])

会起作用,但它会给你一个编译器警告(除非你关闭了这个警告)。

您还可以通过使用双括号来抑制警告:

if((self = [super init]))

我目前的偏好:

self = [super init];
if(self)
于 2013-02-11T20:25:58.590 回答
2

你有一些拼写错误,不平衡的括号,你说的是 ivar 不是 ivar(你在 内声明它if,这使得它的范围在那个块本地。你想把实例变量放在你的or{}之后的 s中声明)。但是,是的,这通常是如何工作的。@implementation@interface

但是,我会仔细研究您是否真的需要 ivar。我不记得上次在我的代码中使用它是什么时候了。我曾经在 99% 的情况下使用它们,a@property现在是一个更好的解决方案。

作为一个额外的好处,@propertys 合成了自己的 getter 和 setter,(通常)避免了编写手动alloc样板的需要,从而使这个问题变得毫无意义。

于 2013-02-11T20:30:15.160 回答
1

1)这段代码可以工作,但这一行:

SomeClass *someIVarObject = [SomeClass alloc] init];

有点道理。在 .h 文件中声明SomeClass *someIVarObject并在 init 中初始化,如下所示:

someIVarObject = [SomeClass alloc] init];

2)这一行if (self = [super init])相当于:

self = [super init]; if (self != nil)

即它确保基类的 init 方法返回了正确的值

于 2013-02-11T20:20:58.227 回答