自定义类的copy语法

2018-12-28  本文已影响0人  薛定谔的汪汪

前言

只有遵守了NSCopying协议的类,才能使用copy语法(也即copy方法,通过一个对象,产生一个同类型的对象)。

自定义类如何实现copy语法?

(1)遵守NSCopying协议

遵守NSCopying协议

(2)实现唯一的一个协议方法

实现协议方法

重点是如何实现协议方法

(1)如果你想让外界这样调用:

    Person *per = [[Person alloc]init];
    per.name  = @"chj";
    per.sex = @"male";
    per.age = 18;
    
    Person *per2 = [per copy];
    NSLog(@" %@,per = %p",per,per);
    NSLog(@" %@,per2 = %p",per2,per2);

那就这样实现:

- (nonnull id)copyWithZone:(nullable NSZone *)zone {
    Person *per = [[Person allocWithZone:zone]init];
    per.name = self.name;    在当前对象内产生新对象并对其完成赋值
    per.sex = self.sex;
    per.age = self.age;
    return per;
}

- (NSString *)description{
    //提供输出方法,否则打印时只会对象打印地址
    return [NSString stringWithFormat:@"name = %@,sex = %@,age = %zd",self.name,self.sex,self.age];
}

(2)如果你想让外界这样调用:

    Person *person = [[Person alloc]initWithName:@"chj" sex:@"male" age:18];
    Person *person2 = [person copy];
    NSLog(@"person = %@,person = %p",person,person);
    NSLog(@"person2 = %@,person2 = %p",person2,person2);

那就这样实现:

- (instancetype)initWithName:(NSString *)name sex:(NSString *)sex age:(NSInteger)age{
    self = [super init];
    if (self) {
        self.name = name;
        self.sex = sex;
        self.age = age;
    }
    return self;
}
- (nonnull id)copyWithZone:(nullable NSZone *)zone {
    Person *person = [[Person allocWithZone:zone]initWithName:self.name sex:self.sex age:self.age];
    return person;
}

总结:
(1)无论哪种实现方式,当【person copy】是都会调用copyWithZone:方法。所以,虽然协议方法不是@required修饰的,但必须实现该方法,要不然达不到【拷贝】对方的目的;
(2)copyWithZone:方法传进去的zone就是对象【拷贝】时有关对象的内存空间,必须要利用该内存区域,否者得不到对方的信息。所以alloc时走的是allocWithZone:方法,按照该内存空间的特有结构去分配新的存储空间;init初始化时,你可以先默认初始化,而后再分别赋值(只能在该方法中);也可以直接初始化(构造方法)
(3)自定类的description方法,默认时打印self,也即只有地址,无法打印详细信息,故最好重写该方法,自定义输出字符串,方便测试。
(4)对拷贝而来的新对象赋值时要知道self代表的是什么,这样才能理解per.name = self.name;的真正意义;

上一篇 下一篇

猜你喜欢

热点阅读