CG@CPPBLOG

/*=========================================*/
随笔 - 76, 文章 - 39, 评论 - 137, 引用 - 0
数据加载中……

用OBJC编程 4 - Customizing Existing Classes

用OBJC编程 4 - Customizing Existing Classes

通过Category为类增加方法
#import "XYZPerson.h"
@interface XYZPerson (XYZPersonNameDisplayAddtions)
- (NSString *)lastNameFirstNameString;
@end
// ----------------------
#import "XYZPerson+XYZPersonNameDisplayAddtions.h"
@implementation XYZPerson (XYZPersonNameDisplayAddtions)
- (NSString *)lastNameFirstNameString{
  
return [NSString stringWithFormat:@"%@ %@", self.lastName, self.firstName];
}
@end
//-------------------------------
#import "XYZPerson+XYZPersonNameDisplayAddtions.h"
@implementation SomeObject
-(void) someMethod{
  XYZPerson *person = [[XYZPerson alloc] initWithFirstName:@"John", lastName:@"Doe"];
  NSLog(@"The people is %@", [person lastNameFirstNameString]);
}
@end

Category 可以增加任何的实例方法和类方法,但是通常不适合增加Property,虽然语法上可以声明一个Property,但不能通过Category增加一个实例变量。这意味着不能synthesize任何实例变量, 也没有存取方法。 你可以写自己的accessor,但是不能keep track property,它们存储在原始的类里。

避免名字冲突
Category 的新增方法可能会导致名字冲突,在运行时可能会出现未知的行为,为了避免这种情况,需要增加前缀
@interface NSSortDescriptor (XYZAdditions)
+ (id)xyz_sortDescriptorWithKey:(NSString *)key ascending:(BOOL)ascending;
@end
//  ------ use it -------
NSSortDescriptor *descriptor = [NSSortDescriptor xyz_sortDescriptorWithKey:@"name" ascending:YES];

类扩展类似分类,但只能用于编译时有源码情况,并且必须写在实现文件里,因此不能通过这个为框架类扩展。扩展语法类似分类
@interface ClassName ()
{
    id _someCustomInstanceVariable;
}
@property NSObject *extraProperty;
@end
也叫匿名分类。不像分类那样,扩展可以增加属性和实例变量。编译器会自动synthesize accessor方法。如果你增加方法,必须实现在主要的@implementation代码块里。

可以用扩展来声明私有属性和方法
@interface XYZPerson:NSObject
@proerty (readonly) NSString *uniqueIdentifier;
-(void)assignUniqueIdentifier;
@end

/// ---------------------

@interface XYZPerson ()
@property (readwrite) NSString *uniqueIdentifier;
@end

@implementation XYZPerson
// ,,,
@end
像上面那样重复声明uniqueIdentifier为readwrite,每一个运行时的XYZPerson对象都将存在一个setter。
任何访问私有方法,或者set一个readonly属性的行为,编译器都会产生错误,但是可以通过动态运行时特性避免编译器错误,诸如调用NSObject的performSelector方法。

如果你打算构建私有方法或属性,你可以声明一个分离的头文件来声明扩展,诸如XYZPerson.h和XYZPersonPrivate.h

分类和扩展并不是定制一个类的唯一途径,也不是最好方法,要考虑可否使用子类化或者委托的方法来实现。


posted on 2013-11-20 18:55 cuigang 阅读(265) 评论(0)  编辑 收藏 引用 所属分类: OBJC


只有注册用户登录后才能发表评论。
网站导航: 博客园   IT新闻   BlogJava   知识库   博问   管理