copyWithZone

草莓味辣妹 关注

2018.08.27 19:54* 字数 533 阅读 979评论 2喜欢 0

copyWithZone

copyWithZone是NSCopying协议的方法,只有实现了copyWithZone方法的对象才能够进行copy的操作。像NSArray、NSMutableArray,NSDictionary、NSMutableDictionary等内部都实现了copyWithZone方法才能进行copy操作。

NSObject类有copyWithZone和MutableCopyWithZone两个类方法,但是其本身并没有实现,它要求子类去实现,子类要调用copy方法进行复制,必须遵循NSCopying协议实现copyWithZone方法,否则会崩溃。

copy有浅拷贝和深拷贝,具体想要实现哪一种,可以在copyWithZone和MutableCopyWithZone方法里面自定义实现。copy和mutableCopy操作分别对应copyWithZone和MutableCopyWithZone方法。

对于不可变对象,浅拷贝为指针拷贝,深拷贝为复制不可变副本

对于可变对象,浅拷贝为不可变副本,深拷贝为可变副本

如果我们想用我们的某个类需要区别对待这两个功能——同时提供创建可变副本和不可变副本的话,一般在NSCopying协议规定的方法 copyWithZone中返回不可变副本;而在NSMutableCopying的mutableCopyWithZone方法中返回可变副本。然后调 用对象的copy和mutableCopy方法来得到副本。

很少自定义可变类型的类,所以我们可以copyWithZone实现指针拷贝或副本拷贝,这完全取决于作者意愿以及业务需求

例如我想将copyWithZone方法用于浅拷贝,即指针拷贝

有一个Product类

@interface Product :NSObject<NSCopying>

@property (strong, nonatomic) NSString* name;

@end

//浅拷贝

@implementation Product

- (id)copyWithZone:(NSZone *)zone {

    return self;

}

@end

或者想将copyWithZone方法用于深拷贝,即副本拷贝

//深拷贝

@implementation Product

- (id)copyWithZone:(NSZone *)zone {

    Product *copy = [[Product allocWithZone] init];

    copy.name = self.name;   //属性赋值,多个属性时同理

    return copy;  //返回副本

}

注意的一点,当Product有子类时,需要这样写Product *copy = [[[self class] allocWithZone] init];

因为copyWithZone会被继承,当子类使用copy方法时,最终会调用到父类的copyWithZone方法

}

allocWithZone

推荐阅读更多精彩内容