'委托'属性可以支持多种协议吗?

时间:2012-05-11 10:07:21

标签: objective-c properties delegates protocols

我可以找到很多关于使对象支持多种协议但没有确认@property是否可以的问题。例如,我有一个属性为:

的类
@property (strong) id dataSource;

这里传入的对象支持UITableViewDataSource协议,所以我可以毫无问题地分配它,在ARC中没有警告:

self.tableView.dataSource = self.dataSource;

我还想实现另一个用于搜索的协议,名为CustomControllerSearchDelegate。但是,如果我开始随机调用其他方法,ARC不出所料地开始抱怨。因此,我们沿着协议道路前进,在我的对象中定义它并使属性支持它。这会导致分配到表数据源时出现问题。所以对于主要问题,我可以这样做:

@property (strong) id <UITableViewDataSource, CustomControllerSearchDelegate> dataSource;

如果不是什么是合适的选择?

或者,为了删除此编译器警告,正确的方法是什么:

Assigning to 'id<UITableViewDataSource>' from incompatible type
'id<PickerViewControllerDataSource>'

如果解释得不好,请道歉。 :/

- 编辑 -

所以我的协议现在被定义为:

@protocol PickerViewControllerDataSource <UITableViewDataSource>

将属性定义为:

@property (strong) id <PickerViewControllerDataSource> dataSource;

然而,编译器抛出以下错误:

No known instance method for selector 'objectAtIndexPath:'

- 编辑 -

以上在自定义协议中声明。宣言现为:

@protocol PickerViewControllerDataSource <UITableViewDataSource>

- (id)objectAtIndexPath:(NSIndexPath *)indexPath;

@optional

- (void)searchDataWithString:(NSString*)string;
- (void)cancelSearch;

@end

谢谢。

1 个答案:

答案 0 :(得分:5)

您可以创建包含其他协议的协议,例如:

@protocol MyDataSourceProtocol <UITableViewDataSource, CustomControllerSearchDelegate>
@end

来自Objective-C Programming Guide

  

一个协议可以使用相同的语法合并其他协议   这些类用于采用协议:

     

@protocol ProtocolName&lt;协议列表&gt;

您的dataSource属性将被定义为:

@property (strong) id <MyDataSourceProtocol> dataSource;

或者,您的CustomControllerSearchDelegate协议可以包含UITableViewDataSource协议:

@protocol CustomControllerSearchDelegate <UITableViewDataSource>
  ... new methods here ...
@end

在这种情况下,您的dataSource属性将被定义为:

@property (strong) id <CustomControllerSearchDelegate> dataSource;

我个人更喜欢后一种方法。