2.3 管理Objective-C世界中的继承
Objective-C入门经典
读者在阅读本书的过程中会发现与其他面向对象语言相比,在Objective-C中实现子类化和继承的方式更多。继承的基本要素是比较简单的,只需要声明一个基对象即可,这个基对象可以拥有自己的方法和实例变量。按照Objective-C程序设计最佳实践的要求,应该将基对象的实例变量声明成对其他类不可见,其他类通过访问器来访问实例变量。
阅读第9章以了解如何使用声明式属性自动生成访问器。
类的方法可以在类接口文件(.h文件)或实现文件(.m文件)中进行声明,在接口文件中声明的方法对其他类是可见的,但可以通过将其声明移到实现文件中来对外部世界隐藏这些方法。在实现文件中隐藏方法有助于提升类的封装性。
阅读第18章中“使用类扩展”一节以了解如何隐藏类的方法。
接着就可以覆写基对象了,每个覆写基对象的类都会继承基对象的方法和变量,并且能够覆写这些方法,这样就能够控制子类如何处理这些方法了。如假设基对象有一个名为init的方法,则子类对该方法的处理方式有3种。
调用—如果基类声明了init,那么当在子类上调用init时实际上调用的是基类的init方法。
覆写—如果在子类中声明了init方法,那么当在子类上调用init方法时实际上调用的是子类的init方法。
覆写并调用—在子类覆写基类的方法时总是可以调用[super init](或者基类的其他方法)。
这意味着在子类中可以合并基类的功能或者替换基类的功能。如果子类化了一个子类,那么可以通过super来调用继承链中该方法的各种实现,直至基类中的实现。从面向对象的角度来看,使用该对象的类看到的是基对象及其所有派生类都以相同或不同的方式实现了某一特定的方法—即抽象对象应该实现的功能(如在银行账号中应该能够报告账号余额)。
上面讨论的内容都是面向对象程序设计的标准。Objective-C通过多种方式对继承的概念进行了扩展。继承和子类化提供了一种有序的方式将其他对象中的代码集成到自己的对象,当然这里所指的其他对象主要是指自己的对象的超类。
Objective-C提供了多种方式将其他结构中的代码集成进自己的对象。除了继承之外,还包括:
协议—这是一组可以被类采纳的方法。采纳协议的类需要实现协议中的方法,一旦一个类采纳了一个协议之后就可以在该类的实例上调用任何协议中的方法了(可以将协议中的方法标记为可选,这样的话在调用时就需要确保只调用那些必须被实现的方法或者被实现的方法)。各个采纳协议的类会以其自己的方式(通常通过其自己的变量)来实现协议。这种协议结构在某种程度上实现了多继承的部分特性。协议中的方法可能会出现在几个毫不相干的类中,从而扩展了通过继承链来共享方法的思想。
分类—协议可以被任何类所采纳,而分类则由一组被添加到某一特定类的方法构成。使用分类可以向一个无源码的既有类中添加方法。
扩展—扩展有时候也被称为匿名分类,它是在类的实现文件(通常是.m文件)中进行声明和实现的。扩展可以向一个类添加方法和属性,还可以重定义属性(如将readonly变成readwrite)。