Objective-C 协议


Objective-C 允许您定义协议,该协议声明预期用于特定情况的方法。协议是在符合协议的类中实现的。

一个简单的例子是网络 URL 处理类,它将有一个协议,其中包含 processCompleted 委托方法等方法,一旦网络 URL 获取操作结束,该协议就会通知调用类。

协议的语法如下所示。

@protocol ProtocolName
@required
// list of required methods
@optional
// list of optional methods
@end

@required关键字下的方法必须在符合协议的类中实现,@optical关键字下的方法是可选实现的。

这是符合协议的类的语法

@interface MyClass : NSObject <MyProtocol>
...
@end

这意味着 MyClass 的任何实例不仅会响应接口中专门声明的方法,而且 MyClass 还会提供 MyProtocol 中所需方法的实现。无需在类接口中重新声明协议方法 - 采用协议就足够了。

如果您需要一个类采用多个协议,您可以将它们指定为逗号分隔的列表。我们有一个委托对象,它保存实现协议的调用对象的引用。

一个例子如下所示。

#import <Foundation/Foundation.h>

@protocol PrintProtocolDelegate
- (void)processCompleted;

@end

@interface PrintClass :NSObject {
   id delegate;
}

- (void) printDetails;
- (void) setDelegate:(id)newDelegate;
@end

@implementation PrintClass
- (void)printDetails {
   NSLog(@"Printing Details");
   [delegate processCompleted];
}

- (void) setDelegate:(id)newDelegate {
   delegate = newDelegate;
}

@end

@interface SampleClass:NSObject<PrintProtocolDelegate>
- (void)startAction;

@end

@implementation SampleClass
- (void)startAction {
   PrintClass *printClass = [[PrintClass alloc]init];
   [printClass setDelegate:self];
   [printClass printDetails];
}

-(void)processCompleted {
   NSLog(@"Printing Process Completed");
}

@end

int main(int argc, const char * argv[]) {
   NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
   SampleClass *sampleClass = [[SampleClass alloc]init];
   [sampleClass startAction];
   [pool drain];
   return 0;
}

现在,当我们编译并运行该程序时,我们将得到以下结果。

2013-09-22 21:15:50.362 Protocols[275:303] Printing Details
2013-09-22 21:15:50.364 Protocols[275:303] Printing Process Completed

在上面的例子中我们已经看到了 delgate 方法是如何被调用和执行的。它从 startAction 开始,一旦流程完成,就会调用委托方法 processCompleted 来通知操作已完成。

在任何 iOS 或 Mac 应用程序中,我们永远不会在没有委托的情况下实现程序。因此,我们了解委托的用法很重要。委托对象应使用 unsafe_unretained 属性类型以避免内存泄漏。