iOS Model模型转换三方调研

2018-04-19  本文已影响96人  spades_K

传统的KVC实现模型转换

定义一个User类
@interface User : NSObject
@property(copy,nonatomic) NSString *name;
@property(copy,nonatomic) NSString *gender;
@property(copy,nonatomic) NSString *age;
@property(copy,nonatomic) NSString *userId;
@property(copy,nonatomic) NSMutableArray *roles;
@end
耗时计算
//
//  ViewController.m
//  ModelConversionContrast
//
//  Created by rck on 2018/4/19.
//  Copyright © 2018年 RCK. All rights reserved.
//

#import "ViewController.h"
#import "Models.h"
#import <MJExtension.h>
#import <YYModel.h>
@interface ViewController ()
@property(strong,nonatomic)NSDictionary *userDict;
@end

// 测试次数
static int testCout = 10;
// 转换次数
static int contrastCout = 10000;

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    
    // KVC耗时(性能最佳 后面就不比对多model嵌套问题了)。
    [self kvcModelContrast];
    
    
    // MJExtension 耗时
    [self mjextensionContrast];
    
    // YYModel耗时
    [self yyModelContrast];
    
    // Do any additional setup after loading the view, typically from a nib.
}


#pragma mark - KVC
- (void)kvcModelContrast
{
    // 定义模型字典
    
    double allTime = 0;
    
    for (int i = 0; i <testCout; i++) {
        // 毫秒
        double stDate = [[NSDate date] timeIntervalSince1970] *1000;
        for (int i = 0; i <contrastCout; i++) {
            User *user = [[User alloc] init];
            [user setValuesForKeysWithDictionary:self.userDict];
        }
        
        // 毫秒
        double edDate = [[NSDate date] timeIntervalSince1970] *1000;
        
        //        NSLog(@"耗时-----%f毫秒",edDate-stDate);
        allTime += (edDate-stDate);
    }
    
    NSLog(@"KVC 单层模型转换 方法执行%d次 循环转换%d次,平均耗时%f毫秒",testCout,contrastCout,allTime/testCout);

}



#pragma mark - 三方获取属性方法
- (void)getAllPropertys
{
    unsigned int propertyCount = 0;
    ///通过运行时获取当前类的属性
    objc_property_t *propertys = class_copyPropertyList([User class], &propertyCount);
    
    //把属性放到数组中
    for (int i = 0; i < propertyCount; i ++) {
        ///取出第一个属性
        objc_property_t property = propertys[i];
        //得到属性对应的名称
        NSString *name = @(property_getName(property));
        
        NSLog(@"name:%@", name);
    }
    
}


#pragma mark - MJEXtension
- (void)mjextensionContrast
{
    // 定义模型字典
    double allTime = 0;
    
    for (int i = 0; i <testCout; i++) {
        // 毫秒
        double stDate = [[NSDate date] timeIntervalSince1970] *1000;
        for (int i = 0; i <contrastCout; i++) {
            User *user = [[User alloc] init];
            [user mj_setKeyValues:self.userDict];
            
            
//             NSLog(@"替换的 id  属性%@ 容器model容器 %@",user.userId,user.roles); // 替换的 id  属性1
        }
        
        // 毫秒
        double edDate = [[NSDate date] timeIntervalSince1970] *1000;
        
        //        NSLog(@"耗时-----%f毫秒",edDate-stDate);
        allTime += (edDate-stDate);
    }
    
    NSLog(@"MJEXtension %@层模型转换 执行%d次 循环转换%d次,平均耗时%f毫秒",self.userDict[@"roles"]?@"多":@"单", testCout,contrastCout,allTime/testCout);

}



#pragma mark YYModel
- (void)yyModelContrast
{
    // 定义模型字典
    double allTime = 0;
    
    for (int i = 0; i <testCout; i++) {
        // 毫秒
        double stDate = [[NSDate date] timeIntervalSince1970] *1000;
        for (int i = 0; i <contrastCout; i++) {
            User *user = [User yy_modelWithJSON:self.userDict];
            
//            NSLog(@"替换的 id  属性%@ 容器model容器 %@",user.userId,user.roles); // 替换的 id  属性1
        }
        
        // 毫秒
        double edDate = [[NSDate date] timeIntervalSince1970] *1000;
        
        //        NSLog(@"耗时-----%f毫秒",edDate-stDate);
        allTime += (edDate-stDate);
    }
    
    NSLog(@"YYModel %@层模型转换 执行%d次 循环转换%d次,平均耗时%f毫秒",self.userDict[@"roles"]?@"多":@"单", testCout,contrastCout,allTime/testCout);

}


#pragma mark - SetterAndGetters
- (NSDictionary *)userDict
{
    return @{@"name":@"Jack",
             @"gender":@"man",
             @"age":@"18",
             @"id":@"1"
             /* 注释下面则为单层model*/
             ,@"roles":@[@{@"name":@"staff"},
                        @{@"name":@"citizen"}]
             };
}


@end
优点:
缺点:
三方框架的优点
时效对比 KVC与MJExtension单层model转换
2018-04-19 15:26:49.905309+0800[2065:491747] KVC 单层模型转换 方法执行10次 循环转换10000次,平均耗时24.895508毫秒
2018-04-19 15:26:52.922414+0800[2065:491747] MJEXtension 单层模型转换 执行10次 循环转换10000次,平均耗时301.692432毫秒

介绍几个主流的iOS转换Model框架

1.MJExtension

MJExtension.png 161d2039c2a5a948.png
代码详解见这里✋
使用方法 全中文注释
引入工程:21个文件80K 量级较大 功能也支持很多比如支持CoreData plist 与Model的转话等。类目较多,如果只是简单的转换 不推荐引入。
常用方法
/**
@implementation User

 key值替换

 @return @{需要的值:替换的值}
 */
+ (NSDictionary *)mj_replacedKeyFromPropertyName
{
    return @{@"userId":@"id"// key对应数组,数组里面为模型
             };
}


/**
 model嵌套问题

 @return @{接受的key值:[需要嵌套在内的类 class]};
 */
+ (NSDictionary *)mj_objectClassInArray
{
    return @{@"roles":[Role class]};
}
@end

YYModel

YYModel.png
代码详解见这里✋1 代码详解见这里✋2
使用方法见这里✋
引入工程:5个文件 120k。
先看下转化效率对比
2018-04-19 16:11:35.197779+0800 ModelConversionContrast[2085:498926] MJEXtension 多层模型转换 执行10次 循环转换10000次,平均耗时822.410645毫秒
2018-04-19 16:11:36.473886+0800 ModelConversionContrast[2085:498926] YYModel 多层模型转换 执行10次 循环转换10000次,平均耗时127.587207毫秒

2018-04-19 16:13:25.193517+0800 ModelConversionContrast[2088:499480] KVC 单层模型转换 方法执行10次 循环转换10000次,平均耗时24.614404毫秒
2018-04-19 16:13:28.180702+0800 ModelConversionContrast[2088:499480] MJEXtension 单层模型转换 执行10次 循环转换10000次,平均耗时298.698267毫秒
2018-04-19 16:13:28.680770+0800 ModelConversionContrast[2088:499480] YYModel 单层模型转换 执行10次 循环转换10000次,平均耗时49.986694毫秒

常用方法
@implementation User

#pragma mark -YYModel
/**
 key值替换问题
 @return  @{接受的key值:[需要嵌套在内的类 class]};
 */
+ (NSDictionary *)modelCustomPropertyMapper {
    return @{@"userId":@"id"};
    
    // 例子 bookID  支持 多个替换值
//    + (NSDictionary *)modelCustomPropertyMapper {
//        return @{@"name"  : @"n",
//                 @"page"  : @"p",
//                 @"desc"  : @"ext.desc",
//                 @"bookID": @[@"id", @"ID", @"book_id"]};
//    }
}


/**
 model替换

 @return 返回容器类中的所需要存放的数据类型 (以 Class 或 Class Name 的形式)。

 */
+ (NSDictionary *)modelContainerPropertyGenericClass {
    return @{@"roles":[Role class]};
    
//    return @{@"roles":@"Role"};

}

@end

上一篇下一篇

猜你喜欢

热点阅读