对象化妆,它是如何构建的?

时间:2009-09-24 13:08:07

标签: objective-c cocoa cocoa-touch

这些都是相当简单的问题,但在继续之前我想在脑子里找到...

@interface BasicTire : NSObject {
}
@end

@interface SnowTire : BasicTire {
}
@end
  1. 当您调用[SnowTire init]时,包含的[super init]调用[BasicTire init],然后调用[NSObject init]? (即运行到父/超类的级联。

  2. 当你[SnowTire alloc]创建一个新对象时,它包含了其superClass的功能。我是否正确地认为你没有创建以某种方式链接的多个对象(例如SnowTire> BasicTire> NSObject)。

  3. 只是想检查......

    加里

3 个答案:

答案 0 :(得分:3)

  1. 是的,通常初始值设定项调用超类初始值设定项。这在init方法的实现中明确完成。虽然可以调用同一类或其超类的其他初始值设定项,但有必要确保"designated initializer"始终被调用。
    如果一个对象没有实现init(或者有问题的初始化程序),那么就会调用超类中的一个(就像使用任何其他方法一样)。这不是很少,因为在Objectve-C中,实例变量总是初始化为零(在alloc中),因此通常没有必要实现专门的init

  2. alloc只分配内存并设置确定对象类的对象的“isa指针”。你得到的是一个未初始化的对象(不是链表),它有所有实例变量(包括超类)的空间。

答案 1 :(得分:2)

  1. 是。每个初始化程序必须调用超类的指定初始化程序,一直到NSObject。每个初始化程序将超级初始化程序的结果分配给self也很重要。由于初始化程序不需要返回将初始化消息发送到的相同实例。

  2. 是。 alloc在堆上为对象实例变量初始化了足够的内存,并用零清除此内存。这样所有指针都将是nil,布尔值false等等。然后它将isa指针设置为新对象的类。

答案 2 :(得分:1)

  

当你调用[SnowTire init]时,包含的[super init]调用[BasicTire init],然后调用[NSObject init]? (即一个级联运行到父/超类。

您同时实施-[SnowTire init]-[BasicTire init],因此您只需查看您的实施即可:

  1. 您的-[SnowTire init]使用[super init]来致电-[BasicTire init]
  2. 您的-[BasicTire init]使用[super init]来致电-[NSObject init]
  3. [super init]总是调用下一个可用的实现,即使它不在您的直接超类中。如果您未实施-[BasicTire init],则[super init]中的-[SnowTire init]表达式将调用-[NSObject init]。这没关系,因为你显然认为BasicTire不需要任何初始化。 (如果确实如此,那么你遗漏-[BasicTire init]就是一个错误。)

      

    当你[SnowTire alloc]创建一个新对象时,它包含了其superClass的功能。我是否正确地认为你没有创建以某种方式链接的多个对象(例如SnowTire> BasicTire> NSObject)。

    是。每个对象都有一个类(在一个名为isa的变量中,如“此实例 SnowTire”),每个类都有一个超类和一个元类。与所有Objective-C方法和C函数一样,-alloc-init每个只返回一个东西 - 在这种情况下,一个实例有一个类。

    因此,例如,当您向雪地轮胎发送gripTheSnow消息时,它会使用SnowTire实施该方法。如果你发送了一条retain消息,那么你没有在SnowTire中实现retain而你没有在BasicTire中实现它,所以它使用了NSObject的实现。运行时从对象的类(在本例中为SnowTire)开始,在类层次结构的直线上搜索,以NSObject等根类结束。