Objective-C中的类别(Category)

本文介绍了Objective-C中的类别(Category)概念,包括其实现方法、如何扩展类的功能以及有名类别和无名类别(类扩展)的区别。通过示例展示了如何在不同的场景下使用类别来组织代码。

Objective-C中的类别(Category)主要有两大功能,一个是将类的相关方法进行分组,另一个是无需继承即可向现有的类添加新的方法以扩展其功能。

例如,您所在的开发团队需要创建一个类,每个团队成员负责类的某一部分功能,例如成员A负责编写对象的创建与释放的方法、成员B负责编写网络通信的方法、成员C负责数据的家在与保存方法等。iOS SDK中大量使用了类别,这里以NSArray类的外部接口声明为例(代码中以...省略了其他方法的接口声明):

[plain]  view plain copy
  1. @interface NSArray : NSObject <NSCopying, NSMutableCopying, NSCoding, NSFastEnumeration>  
  2. - (NSUInteger)count;  
  3. - (id)objectAtIndex:(NSUInteger)index;    
  4. @end  
  5.   
  6. @interface NSArray (NSExtendedArray)  
  7. - (NSArray *)arrayByAddingObject:(id)anObject;  
  8. - (NSArray *)arrayByAddingObjectsFromArray:(NSArray *)otherArray;  
  9. - (NSString *)componentsJoinedByString:(NSString *)separator;  
  10. ...  
  11. @end  
  12.   
  13. @interface NSArray (NSArrayCreation)  
  14. + (id)array;  
  15. + (id)arrayWithObject:(id)anObject;  
  16. ...  
  17. @end  
  18.   
  19. @interface NSArray (NSDeprecated)  
  20. - (void)getObjects:(id __unsafe_unretained [])objects;  
  21. @end  
注意类别的名字在小括号中,并且位于源类名之后。例如NSExtendedArray是类别名称,它扩展了NSArray类。
类别方法的实现格式如下:

[plain]  view plain copy
  1. @implementation NSArray (NSArrayCreation)  
  2. + (id)array  
  3. {  
  4.     ...  
  5. }  
  6. ...  
  7. @end  

类别的实现部分可以放在类的实现文件中,也可以放在额外的实现文件中。

以上介绍的是有名的类别,有名的类别中只能添加静态方法或者实例方法,不能添加成员变量、属性。类别还有一种特殊的使用方式是创建无名的类别(也叫类的扩展),即括号内为空,例如(TestObject是一个类):

[plain]  view plain copy
  1. @interface TestObject ()  
  2. @property int extensionValue;  
  3. -(void)setExtensionName:(NSString*)name;  
  4. @end  

注意到无名类别除了可以添加方法之外,还允许向类添加额外的成员变量和属性,它们的实现需要放在类的实现部分中。例如:

[plain]  view plain copy
  1. @implementation TestObject  
  2. @synthesize value = _value; //实现在类的外部接口中声明的value属性  
  3. @synthesize extensionValue = _extensionValue; //实现在无名类别中声明的extensionValue属性  
  4.   
  5. -(void)setExtensionName:(NSString*)name  
  6. {  
  7.     NSLog(@"%d, %@", _extensionValue, name);  
  8. }  
  9. ...  
  10. //实现其他类的方法  
  11. ...  
  12. @end  
注意无名类别中添加的方法,其访问级别为私有(@private),你可以在其中添加类的内部私有方法和成员。
[plain]  view plain copy
  1. #import "TestClass.h"  
  2.   
  3. int main(int argc, const char * argv[])  
  4. {  
  5.     @autoreleasepool  
  6.     {          
  7.         TestClass* tc1 = [[[TestClass alloc] init] autorelease];  
  8.         tc1.extensionValue = 2; //编译错误,私有成员无法访问  
  9.     }  
  10.     return 0;  
  11. }  
以上代码无法通过编译,原因是在类扩展中定义的成员均为私有。

另外需要注意的是,类别的数量不受限制,一个类可以有很多的类别。类别中定义的方法的优先级高于类中定义的方法,也就是说当你在类别中定义了一个与源类中的签名完全一致的方法时,类别中的方法会完全覆盖源类中的方法,你无法调用源类中的方法。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值