Objective-C 编程语言(3) 定义类---“指定的”初始化方法
2012-01-06 10:20
316 查看
转载请标明出处:http://blog.csdn.net/zhangxingping
重要的一点是需要确保继承而来的初始化方法必须也能正确地对派生类的对象进行初始化。这点通常都是通过重写(override)这些继承而来的初始化方法来实现的。例如,类C作为B的派生类,实现了一个初始化方法:initWithName:fromfile:。那么C类必须确保从B中继承的init和initWithName:这两个方法也能正确地对C类的对象进行初始化。此时,只要在C类中重写继承而来的这两个方法即可:
这样以来,对于C类的实例来说,用init初始化的时候,先调用的是C类的initWithName:,在该方法中调用initWithName:fromFile:,其调用关系如图3-3:
│
┌───────────────────────┐
│
┌─── │ -init │─────┘
│ │ -initWithName: │<────┐
class B │ │ │ │
│ │ │ │
│ │ │ │
│ └───────────────────────┘ │
│ │
│ │
│ │
│ ┌───────────────────────┐ │
└───>│ -initWithName: │ │
┌─── │ │ │
│ │ │ │
class C └──> │-initWithName:fromFile:│─────┘
│ │
│ │
└───────────────────────┘
图3-3
图3-3中忽略了一个很重要的细节。方法initWihtName:fromFile:作为C类的“指定的”初始化方法,其实现需要向super发送消息来完成B对象数据部分的初始化。但是B类中有两个进行初始化的方法,应该调用哪一个呢?这里说明一下不能调用B类的init方法的两个原因:
● 如果调用B类的init方法将会导致方法调用的“死循环“。B类的init方法中调用了C的initWithName:,该方法中调用了initWithName:fromFile:,而在initWithName:fromFile:有调用了B类的init方法。从而形成初始化的”死循环“。
● 这样就没有复用到B类的initWihName:的方法。
原则:类中的“指定的”初始化方法中必须向super发送消息,从而调用其超类的“指定的”初始化方法。
指定的初始化方法是通过向super发送消息相互关联起来的,而其他的初始化方法则是通过向self发送消息来和这些“指定的”初始化方法关联起来的。
图3-4展示了类A,B和C的初始化方法之间的关系。图的左端显示的都是向self发送消息,右端显示的都是向super发送消息:
│
┌───────────────────────┐
│
│ -init │─────┘
│ │<────┐
class A │ │ │
│ │ │
│ │ │
└───────────────────────┘ │
│
│
│
┌───────────────────────┐ │
┌─── │ -init │─────┘
├──> │ -initWithName: │<────┐
class B │ │ │ │
│ │ │ │
│ │ │ │
│ └───────────────────────┘ │
│ │
│ │
│ │
│ ┌───────────────────────┐ │
└───>│ -initWithName: │ │
┌─── │ │ │
│ │ │ │
class C └──> │-initWithName:fromFile:│─────┘
│ │
│ │
└───────────────────────┘
图3-4
注意:B类的init方法中向self发送消息从而调用initWithName:方法。因此当init消息的接收者是B类的对象的时候,会调用B类的initWithName:方法,而当init消息的接收者是C类的对象的时候,则调用的是C类的initWithName:方法。
“指定的”初始化方法
前面小节“初始化时类之间的协调”中的initWithName:方法就是B类的“指定的”初始化方法。所谓的“指定的”初始化方法就是那些能确保所有继承而来的实例变量都能被初始化的方法(通常都是向super发送消息来调用超类的初始化方法)。这种方法是进行初始化的核心,其他的初始化方法通常都会调用这种方法。在Cocoa编程中有这样的一个传统:“指定”的初始化方法通常是最能决定新对象特性的方法(通常情况下它和其他的初始化方法相比较而言参数最多,但也有例外)。重要的一点是需要确保继承而来的初始化方法必须也能正确地对派生类的对象进行初始化。这点通常都是通过重写(override)这些继承而来的初始化方法来实现的。例如,类C作为B的派生类,实现了一个初始化方法:initWithName:fromfile:。那么C类必须确保从B中继承的init和initWithName:这两个方法也能正确地对C类的对象进行初始化。此时,只要在C类中重写继承而来的这两个方法即可:
-initWithName:(char *)string { return [self initWithName:string fromFile:NULL]; }在上面C类对initWithName:方法的重写中实际上是调用了initWithName:fromFile:这个初始化方法。
这样以来,对于C类的实例来说,用init初始化的时候,先调用的是C类的initWithName:,在该方法中调用initWithName:fromFile:,其调用关系如图3-3:
│
┌───────────────────────┐
│
┌─── │ -init │─────┘
│ │ -initWithName: │<────┐
class B │ │ │ │
│ │ │ │
│ │ │ │
│ └───────────────────────┘ │
│ │
│ │
│ │
│ ┌───────────────────────┐ │
└───>│ -initWithName: │ │
┌─── │ │ │
│ │ │ │
class C └──> │-initWithName:fromFile:│─────┘
│ │
│ │
└───────────────────────┘
图3-3
图3-3中忽略了一个很重要的细节。方法initWihtName:fromFile:作为C类的“指定的”初始化方法,其实现需要向super发送消息来完成B对象数据部分的初始化。但是B类中有两个进行初始化的方法,应该调用哪一个呢?这里说明一下不能调用B类的init方法的两个原因:
● 如果调用B类的init方法将会导致方法调用的“死循环“。B类的init方法中调用了C的initWithName:,该方法中调用了initWithName:fromFile:,而在initWithName:fromFile:有调用了B类的init方法。从而形成初始化的”死循环“。
● 这样就没有复用到B类的initWihName:的方法。
原则:类中的“指定的”初始化方法中必须向super发送消息,从而调用其超类的“指定的”初始化方法。
指定的初始化方法是通过向super发送消息相互关联起来的,而其他的初始化方法则是通过向self发送消息来和这些“指定的”初始化方法关联起来的。
图3-4展示了类A,B和C的初始化方法之间的关系。图的左端显示的都是向self发送消息,右端显示的都是向super发送消息:
│
┌───────────────────────┐
│
│ -init │─────┘
│ │<────┐
class A │ │ │
│ │ │
│ │ │
└───────────────────────┘ │
│
│
│
┌───────────────────────┐ │
┌─── │ -init │─────┘
├──> │ -initWithName: │<────┐
class B │ │ │ │
│ │ │ │
│ │ │ │
│ └───────────────────────┘ │
│ │
│ │
│ │
│ ┌───────────────────────┐ │
└───>│ -initWithName: │ │
┌─── │ │ │
│ │ │ │
class C └──> │-initWithName:fromFile:│─────┘
│ │
│ │
└───────────────────────┘
图3-4
注意:B类的init方法中向self发送消息从而调用initWithName:方法。因此当init消息的接收者是B类的对象的时候,会调用B类的initWithName:方法,而当init消息的接收者是C类的对象的时候,则调用的是C类的initWithName:方法。
相关文章推荐
- Objective-C 编程语言(3) 定义类---分配并初始化对象,init方法的返回值,初始化方法的实现
- Objective-C 编程语言(3) 定义类---分配并初始化对象,init方法的返回值,初始化方法的实现
- Objective-C 中便利初始化方法和指定初始化方法
- Objective-C 编程语言(3) 定义类---把对象的分配和初始化进行合并
- Objective-C基础知识之(四):实例变量的可变度、初始化方法的声明、self和super的具体应用
- Objective-C的Initialize初始化方法研究
- Objective-C学习笔记(二十二)——初始化方法init的重写与自定义
- Objective-C中获取视频指定帧的方法
- Objective-C对象初始化 、 实例方法和参数 、 类方法 、 工厂方法 、 单例模式
- 指定类型构造方法以外的初始化方法
- Objective-c 中如何重写父类的初始化方法
- Objective-C的Initialize初始化方法研究
- 关于ligerUi的ligertree的初始化默认选中指定项目的方法
- [Objective-C] 03.OC中的继承和初始化方法
- Objective-c 构造方法(初始化方法)
- objective-C编程 初始化方法摘要
- IOS-usr/include-objc-NSObject-指定初始化方法
- Objective-C中的方法重载与初始化方法
- Objective-C和Swift中初始化方法比较
- Objective-C的Initialize初始化方法研究