2011-12-30 48 views
0

DataController.h两个接口?

@class Play; 

@interface DataController : NSObject 

- (unsigned)countOfList; 
- (Play *)objectInListAtIndex:(unsigned)theIndex; 

@end 

DataController.m

#import "DataController.h" 
#import "Play.h" 


@interface DataController() 
@property (nonatomic, copy, readwrite) NSMutableArray *list; 
- (void)createDemoData; 
@end 


@implementation DataController 

@synthesize list; 


- (id)init { 
    if (self = [super init]) { 
     [self createDemoData]; 
    } 
    return self; 
} 

为什么你认为@interface被定义了两次?还有什么()的含义?不应该有一个类名称,也许是括号之间的超类?

+1

见http://stackoverflow.com/questions/862299/how- do-a-category-work-in-objective-c – XJones 2011-12-31 00:01:11

回答

7

通常,语法@interface ClassName (CategoryName)用于声明一个类别。类别是向类中添加方法的一种方式。即使对于没有源代码的类,也可以这样做。查看更多here

@interface ClassName()(在括号中没有任何内容)本质上是一个类别的特殊情况,称为类扩展。类扩展和类别之间的主要区别在于,在类扩展中声明的方法必须在类的主@implementation块中定义/实现,否则会得到编译器警告。常规类别中的方法可以在外部@implementation块中定义。

类扩展(在这种情况下)最常见的用途是声明私有方法。 Objective-C不支持真正的私有方法,因此实现相同基本最终结果的简单方法是在.m文件顶部的类扩展中声明私有方法。由于这些方法没有在.h文件中定义,所以其他类将不会看到它们,并且如果您尝试在它们所属的类之外使用它们,将会收到编译器警告。

您还可以在类扩展中重新声明readonly @property为readwrite。这样,类实现外部的代码只能读取属性的值,但在类的实现中,也可以写入它。这是唯一可以重新声明@property的情况。

(请注意,类扩展是在Objective-C 2.0中的新功能,它们不能在Mac OS X 10.4及更早版本。)

+1

你提到**重新声明**'@ property'来改变生成的访问器,但是你没有提到你可以简单地**声明**'@ property'类扩展。 – 2011-12-31 00:40:30

+0

这是一个很好的答案,但是,我会将'@interface ClassName(ProtocolName)'更改为'@interface ClassName(CategoryName)',以避免类别和协议之间的混淆。 – EmilioPelaez 2011-12-31 00:53:45

+0

@EmilioPelaez这是一个愚蠢的错字,我已经修复它。感谢您的支持。值得一提的是,类别有时用于声明非正式协议...... – 2011-12-31 01:23:40

相关问题