文章 iOS自定义对象及子类及模型套模型的拷贝、归档存储的通用代码
Post
Cancel

iOS自定义对象及子类及模型套模型的拷贝、归档存储的通用代码

runtime实现通用copy

如果自定义类的子类,模型套模型你真的会copy吗,小心有坑。 copy需要自定义类继承NSCopying协议

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
#import <objc/runtime.h>

- (id)copyWithZone:(NSZone *)zone {
    id obj = [[[self class] allocWithZone:zone] init];
    Class class = [self class];
    while (class != [NSObject class]) {
        unsigned int count;
        Ivar *ivar = class_copyIvarList(class, &count);
        for (int i = 0; i < count; i++) {
            Ivar iv = ivar[i];
            const char *name = ivar_getName(iv);
            NSString *strName = [NSString stringWithUTF8String:name];
            //利用KVC取值
            id value = [[self valueForKey:strName] copy];//如果还套了模型也要copy呢
            [obj setValue:value forKey:strName];
        }
        free(ivar);
        class = class_getSuperclass(class);//记住还要遍历父类的属性呢
    }
    return obj;
}

runtime实现通用归档解档

归档解档需要自定义类继承NSCoding协议

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
#import <objc/runtime.h>

#pragma mark - 归档、解档
- (void)encodeWithCoder:(NSCoder *)encoder {
    Class class = [self class];
    while (class != [NSObject class]) {
        unsigned int count;
        Ivar *ivar = class_copyIvarList(class, &count);
        for (int i = 0; i < count; i++) {
            Ivar iv = ivar[i];
            const char *name = ivar_getName(iv);
            NSString *strName = [NSString stringWithUTF8String:name];
            //利用KVC取值
            id value = [self valueForKey:strName];
            [encoder encodeObject:value forKey:strName];
        }
        free(ivar);
        class = class_getSuperclass(class);//记住还要遍历父类的属性呢
    }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
- (id)initWithCoder:(NSCoder *)decoder {
    self = [super init];
    if (self) {
        Class class = [self class];
        while (class != [NSObject class]) {
            unsigned int count = 0;
            //获取类中所有成员变量名
            Ivar *ivar = class_copyIvarList(class, &count);
            for (int i = 0; i < count; i++) {
                Ivar iva = ivar[i];
                const char *name = ivar_getName(iva);
                NSString *strName = [NSString stringWithUTF8String:name];
                //进行解档取值
                id value = [decoder decodeObjectForKey:strName];
                //利用KVC对属性赋值
                [self setValue:value forKey:strName];
            }
            free(ivar);
            class = class_getSuperclass(class);//记住还要遍历父类的属性呢
        }
    }
    return self;
}
This post is licensed under CC BY 4.0 by the author.