利用Runtime实现字典转模型

2017-06-17  本文已影响0人  zhifan_young

参考自:http://www.jianshu.com/p/836f07bb468e

  • Runtime 是一种面向对象编程语言的运行环境
  • OC最主要的特点就是在程序运行时,以发送消息的方式调用方法(也就是常说的OC是基于运行时的)

一句话概括:通过 Runtime 获取 model 的属性列表,然后遍历字典中的 key,如果属性列表中包含这个 key 则通过 KVC 把字典中对应的 value 赋值到 model 的属性。

字典转模型核心算法思路.png

为什么要利用 Runtime 来进行字典转模型:

首先获取属性列表。
const char *key = "key";

+ (NSArray *)getPropertyArr {
    
    // 获取关联对象
    NSArray *proArr = objc_getAssociatedObject(self, key);
    if (proArr) return proArr; // 如果有值,直接返回
    
    // 调用运行时方法,获取类的属性列表
    /* 成员变量:
     * class_copyIvarList(__unsafe_unretained Class cls, unsigned int *outCount)
     * 方法:
     * class_copyMethodList(__unsafe_unretained Class cls, unsigned int *outCount)
     * 属性:
     * class_copyPropertyList(__unsafe_unretained Class cls, unsigned int *outCount)
     * 协议:
     * class_copyProtocolList(__unsafe_unretained Class cls, unsigned int *outCount)
     */
    
    unsigned int count = 0;
    
    // retain, creat, copy 需要release
    objc_property_t *property_List = class_copyPropertyList([self class], &count);
    NSMutableArray *mtArr = [NSMutableArray array];
    
    // 遍历属性列表, 获取属性名称
    for (int i = 0; i < count; i ++) {
        
        objc_property_t pro = property_List[i];
        const char *proName_c = property_getName(pro);
        NSString *proName = [NSString stringWithCString:proName_c encoding:NSUTF8StringEncoding];
        [mtArr addObject:proName];
    }
    
    // 设置关联对象
     objc_setAssociatedObject(self, key, mtArr, OBJC_ASSOCIATION_RETAIN_NONATOMIC);
    
    free(property_List);
    return mtArr;
}

关键步骤:

获取到属性列表后,进行字典转模型。
+ (instancetype)modelWithDic:(NSDictionary *)dic {
    
    // 实例化当前对象
    id objc = [[self alloc] init];
    
    // 获取self 的属性列表
    NSArray *proArr = [self getPropertyArr];
    
    // 遍历字典
    [dic enumerateKeysAndObjectsUsingBlock:^(id  _Nonnull key, id  _Nonnull obj, BOOL * _Nonnull stop) {
       
        // 判断 属性列表中是否包含这个 key
        if ([proArr containsObject:key]) {
            
            // 如果包含通过 KVC 赋值到 model
            [objc setValue:obj forKey:key];
        }
    }];
    return objc;
}

现在就可以定义一个模型,进行字典转模型了

- (void)viewDidLoad {
    [super viewDidLoad];
    
    NSDictionary *dic = @{
                          @"name": @"小李",
                          @"title": @"司机"
                          };
    Person *personModel = [Person modelWithDic:dic];
    
    NSLog(@"%@ --- %@", personModel.name, personModel.title);
    
}
转换结果

这就是一些第三方框架,例如 YYModel,MJExtension等的核心算法,希望在用的时候能明白其中的原理。
代码地址:https://github.com/zhifanYoung/json2model-Demo.git

上一篇下一篇

猜你喜欢

热点阅读