协议(Protocol)讲解
协议是一组没有实现的方法列表,任何的类均可采纳协议并具体实现这组方法。
Objective-C在NeXT时期曾经试图引入多重继承的概念,但由于协议的出现而没有实现。
协议类似于 Java 与 C# 语言中的"接口"。在 Objective-C 中,有两种定义协议的方式:由编译器保证的"正式协议",以及为特定目的设定的"非正式协议"。
非正式协议为一个可以选择性实现的一系列方法列表。非正式协议虽名为协议,但实际上是挂于NSObject上的未实现分类(Unimplemented Category)的一种称谓,Objetive-C语言机制上并没有非正式协议这种东西,OSX 10.6版本之后由于引入 @optional 关键字,使得正式协议已具备同样的能力,所以非正式协议已经被废弃不再使用。
正式协议类似于 Java 中的"接口",它是一系列方法的列表,任何类都可以声明自身实现了某个协议。在Objective-C 2.0之前,一个类必须实现它声明匹配的协议中的所有方法,否则编译器会报告错误,表明这个类没有实现它声明匹配的协议中的全部方法。Objective-C 2.0版本允许标记协议中某些方法为可选的(Optional),这样编译器就不会强制实现这些可选的方法。
协议经常应用于 Cocoa 中的委托及事件触发。例如文本框类通常会包括一个委托(delegate)对象,该对象可以实现一个协议,该协议中可能包含一个实现文字输入的自动完成方法。若这个委托对象实现了这个方法,那么文本框类就会在适当的时候触发自动完成事件,并调用这个方法用于自动完成功能。
Objective-C 中协议的概念与 Java 中接口的概念并不完全相同,即一个类可以在不声明它匹配某个协议的情况下,实现这个协议所包含的方法,也即实质上匹配这个协议,而这种差别对外部代码而言是不可见的。正式协议的声明不提供实现,它只是简单地表明匹配该协议的类实现了该协议的方法,保证调用端可以安全调用方法。
语法
协议以关键字 @protocol 作为区块起始,@end 结束,中间为方法列表。
注⚠️:关键字并不能严格的控制某一个遵守该协议的类必须要实现该方法, 因为即便不是实现也不会报错, 只会报一个警告。
这是一个协议的例子,多线程编程中经常要确保一份共享资源同时只有一个线程可以使用,会在使用前给该资源挂上锁 ,以上即为一个表明有"锁"的概念的协议,协议中有两个方法,只有名称但尚未实现。
下面的SomeClass宣称他采纳了Locking协议:
一旦SomeClass表明他采纳了Locking协议,SomeClass就有义务实现Locking协议中的两个方法。
由于SomeClass已经确实遵从了Locking协议,故调用端可以安全的发送lock或unlock消息给SomeClass实体变量,不需担心他没有办法回应消息。
当某个类遵守了某个协议,但并不意味着:它就一定要实现它,因为不实现也不报错。当这个类被实例化,意味着可以调用其遵守的协议方法,但如果没有实现就会报错,所以要使用respondsToSelector
进行判断是否实现了某些协议方法。
协议的使用特点
-
父类遵守了某个协议,那么子类也自动遵守此协议
父类遵守了此协议
子类自然遵守此协议
-
协议可以遵守协议
一个协议遵守了另一个协议,就可以拥有另一份协议中的方法声明。
-
基协议
每个协议都应该遵守 NSObject
协议,它是一个基协议,最根本的协议。
OC 是单继承
,但是一个类可以遵守一个或多个协议。
总结:
- 协议只有声明文件;
- 在遵守协议的类中导入协议的文件,并添加遵守协议 在 @interface 后面加尖括号遵守协议;
- @required 必须在 .m 中实现, @optional 可以不用实现,也即遵守协议做事情;
- 原本类(Nurse.h)中 写@interface Nurse : NSObject <NurseWorkingProtocol>
- 点赞
- 收藏
- 关注作者
评论(0)