Customizing Existing Classes (对现有类进行修改及扩展)
CategoriesAdd Methods to Existing Classes
XYZPerson.h文件(声明了XYZPerson类)
@interface XYZPerson:NSObject;
-(void)sayHello;
@end
XYZPerson.m文件(XYZPerson的实现)
#import "XYZPerson.h"
@implementation XYZPerson
XYZPerson+XYZPersonNameDisplayAdditions.h (声明了XYZPerson的CateGories 对 XYZPerson类进行扩展)
括号内是category的名字
#import "XYZPerson.h"
@interface XYZPerson (XYZPersonNameDisplayAdditions)
- (NSString *)lastNameFirstNameString;
@end
XYZPerson+XYZPersonNameDisplayAdditions.m(Categories的实现)
#import "XYZPerson+XYZPersonNameDisplayAdditions.h"
@implementation XYZPerson (XYZPersonNameDisplayAdditions)
- (NSString *)lastNameFirstNameString {
return [NSString stringWithFormat:@"%@, %@", self.lastName, self.firstName];
}
@end
其他任何类中引用XYZPerson+XYZPersonNameDisplayAdditions.h就可以实例化并使用这个类及其在categories中追加的方法了
#import "XYZPerson+XYZPersonNameDisplayAdditions.h"
@implementation SomeObject
- (void)someMethod {
XYZPerson *person = [[XYZPerson alloc] initWithFirstName:@"John"
lastName:@"Doe"];
XYZShoutingPerson *shoutingPerson =
[[XYZShoutingPerson alloc] initWithFirstName:@"Monica"
lastName:@"Robinson"];
NSLog(@"The two people are %@ and %@",
[person lastNameFirstNameString], [shoutingPerson lastNameFirstNameString]);
}@end
Avoid Category Method Name Clashes
@interface NSSortDescriptor (XYZAdditions)
- (id)xyz_sortDescriptorWithKey:(NSString *)key ascending:(BOOL)ascending;
@end
NSSortDescriptor *descriptor =
[NSSortDescriptor xyz_sortDescriptorWithKey:@"name" ascending:YES];
ClassExtensions Extend the Internal Implementation
XYZPerson.m
@interface XYZPerson () {
id _someCustomInstanceVariable;//定义实例变量
}...
@property NSObject *extraProperty;//定义属性
@end
@implements XYZPerson
...
@end
Use Class Extensions to Hide Private Information
@interface XYZPerson : NSObject
...
@property (readonly) NSString *uniqueIdentifier;
- (void)assignUniqueIdentifier;
@end
.m文件
@interface XYZPerson ()
@property (readwrite) NSString *uniqueIdentifier;
@end
@implementation XYZPerson
...
@end
那么该extension所在的implements中此属性uniqueIdentifier就被改为了readwrie
个人理解是:当外部类实例化本类时uniqueIdentifier属性是readonly的,而在带有上面extension的本类实现中uniqueIdentifier却是readwrite的,类似于(java中的private)
考虑类的重用性,你可以使用继承创建子类,或者使用代理(delegate)对象(后一篇会学习,这里还不是很明白)Consider Other Alternatives for Class Customization
哪个函数被调用,那个信息被送出,都不是在编译的时候,而是在运行时候被决定的。Interact Directly with the Objective-C Runtime
obj-c的运行时系统,比如extension和associative reference(相关引用)不影响原始类的定义和实现。
总结:category只用来作为对源生类的扩展,单独.h和.m文件
extension只写在.m文件中,不被外界调用的属性和方法基本都写在extension内