原文:http://mobile.51cto.com/iphone-269848.htm
Mac OS X包含多个Cocoa框架,苹果和第三方厂商也随时会发布更多的框架。无论Cocoa框架有多么丰富,有两个框架总是与众不同:即Foundation和Application Kit框架,它们是核心的Cocoa框架。
AD:
是什么因素使一个程序成为Cocoa程序呢?肯定不是编程语言,因为在Cocoa开发中您可以使用各种语言;也不是开发工具,因为您在命令行上就可以创建Cocoa程序(虽然那会使开发过程变得复杂,且需要消耗大量时间)。那么,所有Cocoa程序的共同点是什么?是什么使它们变得与众不同?答案是这些程序都是由一些对象组成,而这些对象最终都是从NSObject这个根类继承下来的;还有,这些程序都是基于Objective-C运行环境的。这个说法对于所有的Cocoa框架来说也是正确的。
请注意:上面的说法还需要做一点限制。首先,Cocoa还有另一个根类,即NSProxy。只是NSProxy很少用于Cocoa编程。其次,您可以创建您自己的根类,只是这需要很多工作(包括编写与Objective-C运行环境进行交互的代码),而且为此花费时间可能是不值得的。
Mac OS X包含多个Cocoa框架,苹果和第三方厂商也随时会发布更多的框架。无论Cocoa框架有多么丰富,有两个框架总是与众不同:即Foundation和Application Kit框架,它们是核心的Cocoa框架。如果您没有连接并使用Application Kit框架中的类,就不能开发任何类型的Cocoa软件;同样地,如果您没有连接并使用Foundation框架中的类,也不能开发任何类型的Cocoa软件(当您连接Cocoa雨伞框架的时候,Xcode会自动连接这些框架)。Foundation和Application Kit框架在Cocoa开发中是必要的,其它框架则是辅助和可选的。
下面的部分将讨论上述两个核心的Cocoa框架,并简要描述一些辅助性的框架。为了使这些大框架更加容易理解,在介绍Foundation和Application Kit框架时,我们将每个层次中的数十个类分为不同的功能组。虽然这种分组方式有很强的逻辑基础,但是人们也可以按其它方式合理地进行分组。
Foundation
Foundation框架定义了一些基础类,可以用于各种类型的Cocoa程序。Foundation框架和Application Kit框架的区分标准在于用户界面。如果一个对象既不出现在用户界面上,也不是专门用于支持用户界面,那么它就属于Foundation框架。您可以仅用Foundation框架创建一个Cocoa程序,而不涉及其它框架;命令行工具和Internet服务器就是这样的例子。
苹果公司在设计Foundation框架时牢记如下目标:
为诸如内存管理、对象改变、和通告这样的事物定义基本的对象行为和引入一致的规则。
通过程序包技术和Unicode字符串(和其它技术一起)支持国际化和本地化。
支持对象的持久保存。
支持对象的分发。
在一定程度上独立于操作系统,以支持移植。
为编程的元类型提供对象封装或等价物,比如数值、字符串、和集合,以及为访问底层系统实体和服务提供工具类,比如端口、线程、和文件系统。
Cocoa应用程序定义为需要连接Application Kit框架,同时也总是必须连接Foundation框架的程序。这两个类层次都共用同一个根类,即NSObject类,很多(如果不是绝大多数的话)Application Kit的方法和函数都将Foundation对象作为参数或返回值。一些Foundation类可能看起来像是为应用程序设计的,NSUndoManager和NSUserDefaults类就是其中的两个例子,但是由于它们没有涉及到用户界面,所以被包含在Foundation框架中。
Foundation的范式和策略
Foundation为Cocoa编程引入了几个范式和策略,以保证程序中的对象在特定的环境下具有一致的行为和期望。包括:
对象的所有权和对象的清除。Foundation建立了一个对象所有权策略,用以代替垃圾收集机制。该策略指定对象需要释放自己创建、拷贝、或显式保留的其它对象。NSObject(类和协议)定义了保留和释放对象的方法。自动释放池(在NSAutoreleasePool类中定义)实现了一种迟缓释放(delayed-release)机制,使Cocoa程序在处理不由调用者负责的返回对象上有一个一致的规则。
可变类的变体。在Foundation中,很多值和容器类的不可变类都有一个可以修改的变体,可变类总是不可变类的子类。如果您需要动态地改变一个经过封装的值,或者改变这种对象的所属关系,可以创建一个可变类的实例。由于它是从相应的不可变类继承下来的,所以您可以在接受不可变类型参数的方法中传入可变类的实例。对象可变性的更多信息请参见"对象的可变性"部分。
类簇。类簇是一个抽象类及一组私有的具体子类的组合,抽象类是这些子类的雨伞接口。根据不同的上下文(特别是创建对象所用的方法),类簇可以为您返回恰当的、经过优化的类实例。举例来说,NSString和NSMutableString就是针对不同的存储需要进行优化的各种私有子类实例的经纪类。多年来,具体类进行了几次修改,但应用程序依然可以工作。类簇的更多信息请参见"类簇"部分。
通告。通告是Cocoa的主要设计模式。它基于广播机制,该机制使一个对象(称为观察者)可以在另一个对象进行某种任务或遇到某种情况时,以用户或系统事件的方式得到通告。产生通告的对象可能并不知道通告观察者的存在或身份。有几种类型的通告:同步、异步、和分布式通告。Foundation的通告机制由NSNotification、NSNotificationCenter、NSNotificationQueue、和NSDistributedNotificationCenter类实现的。更多关于通告的信息请参见"通告"部分。
Foundation类
Foundation类层次的根是NSObject类,它(和NSObject及NSCopying协议一起)定义了基本的对象属性和行为。更多有关NSObject和基本对象行为的信息请参见"根类"部分。
Foundation框架的剩余部分由几组相互关联的类和一些独立的类组成。有一些代表基本数据类型的类,如字符串、字节数组、用于存储其它对象的集合类;一些代表系统信息的类,如日期类;还有一些代表系统实体的类,比如端口、线程、和进程。下图所示的类层次描述了这些类的逻辑分组及其继承关系。
下图为Foundation类层次—Objective-C(第一部分)
下图为Foundation类层次—Objective-C(第二部分)
下图为Foundation类层次—Objective-C(第三部分)
上面这些框图按照如下范畴(和下文提到的其它关联关系)将Foundation框架中的类进行逻辑分类:
值对象。值对象封装了各种类型的数据,提供对数据进行访问和各种操作的途径。因为它们都是对象,所以可以对它们(和它们包含的数值)进行归档和分发。NSData类为字节流提供面向对象的存储空间,而NSValue和NSNumber类则为简单的标量值数组提供面向对象的存储空间。NSDate、NSCalendarDate、NSTimeZone、NSCalendar、NSDateComponents、和 NSLocale类提供代表时间、日期、日历、和地域设置(locales)的对象。它们包含的方法可以用于计算日期和时间差、以各种格式显示日期和时间、以及调整世界上各个位置时间和日期。
字符串。NSString是另一类值对象,负责为以null结尾的、具有特定编码的字节数组提供面向对象的存储空间。它支持对UTF-16、UTF-8、MacRoman、和很多其它编码的字符串之间进行转换。NSString还提供对字符串进行检索、组合、和比较、以及对文件系统路径进行操作的方法。您可以用NSScanner对象来对NSString对象中的数字和词进行解析。NSCharacterSet(显示在框图中的集合类部分)代表可以在各个NSString和NSScanner方法中使用的一组字符。
集合。集合是以一定的顺序存储和访问其它对象(通常是数值)的对象。NSArray的索引从0开始,NSDictionary使用键-值对,而NSSet则负责对象的随机存储(NSCountedSet类使集合具有唯一标识)。通过NSEnumerator对象,您可以访问一个集合中的元素序列。集合对象是属性列表的必要元素,和其它所有对象一样,它也可以被归档和分发。
操作系统服务。 很多Foundation类为访问各种底层的操作系统服务提供便利,同时又把开发者从操作系统的具体特性隔离开来。举例来说,您可以通过NSProcessInfo类查询应用程序运行的环境;通过NSHost类得到主机系统在网络中的名称和地址;通过NSTimer对象,您可以按指定的时间间隔向其它对象发送消息;NSRunLoop可以帮您管理应用程序或其它类型程序的输入源;而NSUserDefaults则为存储全局(主机级别)和用户级缺省值(预置)的系统数据库提供编程接口。
文件系统和URL。 NSFileManager为诸如创建、重命名、删除、和移动文件这样的文件操作提供统一的接口。NSFileHandle则可以进行较为底层的文件操作(比如文件内查找操作)。NSBundle可以寻找存储在程序包中的资源,可以动态装载某些资源(比如nib文件和代码)。您可以用NSURL和NSURLHandle类来表示、访问、和管理源于URL的数据。
进程间通讯。 这个范畴中的大部分类代表不同的系统端口、套接字、和名字服务器,对实现底层的IPC很有用。NSPipe代表一个BSD管道,即一种进程间的单向通讯通道。
线程和子任务。 NSThread类使您可以创建多线程的程序,而各种锁(lock)类则为彼此竞争的线程在访问进程资源时提供各种控制机制。通过NSTask,您的程序可以分出一个子进程来执行其它工作或进行进度监控。
通告。请见"Foundation的范式和策略"部分中的有关通告类总结。
归档和序列化。这个范畴中的类使对象分发和持久保留成为可能。NSCoder及其子类和NSCoding协议一起,可以以独立于架构的方式来表示对象中包含的数据,可以将类信息和数据一起存储。
表达式和条件判断。条件判断类,即NSPredicate、NSCompoundPredicate、和NSComparisonPredicate类,负责对获取或过滤对象的逻辑约束条件进行封装。NSExpression对象则代表条件判断中的表达式。
Spotlight查询。NSMetadataItem、NSMetadataQuery和相关的查询类对文件系统的元数据进行封装,使元数据的查询成为可能。
Objective-C语言服务。NSException和NSAssertionHandler类为代码中的断言和例外处理提供了面向对象的封装。NSInvocation对象是Objective-C消息的静态表示,您的程序可以对它存储,并在之后用于激活另一个对象的消息。undo管理器(NSUndoManager)和分布式对象(Distributed Objects)系统都用到了这种对象。NSMethodSignature对象负责记录方法的类型信息,可以用于信息的推送。NSClassDescription则是一个抽象类,用于定义和查询类的关系和属性。
脚本。这个范畴中的类可以帮助您实现对AppleScript脚本和Apple Event命令的支持。
分布式对象。 您可以通过分布式对象类来进行同一台电脑或一个网络中的不同电脑上的进程间通讯。其中的两个类-NSDistantObject和NSProtocolChecker的根类(NSProxy)和Cocoa其它部分的根类不同。
网络。NSNetService和NSNetServiceBrowser类支持称为Bonjour的零配置网络架构。Bonjour是在IP网络上发布和浏览服务的强大系统。