iosiOS工具&效率&优化iOS 开发每天分享优质文章

通过Rumtime实现打印/Po出模型值

2016-11-07  本文已影响196人  再见远洋

今天我们来谈一谈开发时的debug技巧吧,大家都知道,我们在开发中,使用NSLog("%@",你的模型),这样打印出来的是模型的地址:

**2016-11-07 10:56:16.672 ****测试****[717:27180] <YJYYNewModel: 0x7fb211f13f80>**

这个应该都经历过吧,可能遇到这种情况,一般我们会这么处理,打个断点,然后将鼠标放到写模型的的位置:

屏幕快照 2016-11-07 上午10.56.06.png

布吉岛你们看完上面的步骤作何感想,反正我是感觉好麻烦,主要是有时候你将鼠标放上面不一定出来,好了 ,还是不多说了,还是看看咱么怎么去做吧,一般遇到这种问题,我们的解决方案是通过重写 模型的- (NSString *)description方法:

- (NSString *)description {
    
    return [NSString stringWithFormat:@"text:%@--index:%zi",self.name,self.age];
}

这时候我们再看打印:

**2016-11-07 11:06:46.808 ****测试****[769:35597] text:****随便起的****--index:10**

是不是灰常的神奇,好吧,这个方法,我相信很多人都是知道的,那么还是回到今天的主题,毕竟今天咱们是要用到运行时的,好像目前为止还没有用到Rumtime的地方,别急,马上就来了。

我们再来假设一种情况,当我们的属性有非常非常多的的时候,假如30个,好吧,30个的情况应该也是有的,可能模型嵌套嘛,那这时候,我们该怎么处理?难道还是一个一个拼接吗?显然这不合理,那么我么很理所当然的就想到了Rumtime了,如下:

//
//  YJYYNewModel.m
//  测试
//
//  Created by 遇见远洋 on 16/11/7.
//  Copyright © 2016年 遇见远洋. All rights reserved.
//

#import "YJYYNewModel.h"
#import <objc/runtime.h>

@implementation YJYYNewModel

- (NSString *)description {
    
     NSMutableDictionary *dictionary = [NSMutableDictionary dictionary];
    
    // 获取当前类的所有属性
    unsigned int count;// 记录属性个数
    objc_property_t *properties = class_copyPropertyList([self class], &count);
    for (int i = 0; i < count; i++) {
        
        // An opaque type that represents an Objective-C declared property.
        // objc_property_t 属性类型
        objc_property_t property = properties[i];
        // 获取属性的名称 C语言字符串
        const char *cName = property_getName(property);
        // 转换为Objective C 字符串
        NSString *name = [NSString stringWithCString:cName encoding:NSUTF8StringEncoding];

        id value = [self valueForKey:name]?:@"nil"; [dictionary setObject:value forKey:name];
        
         [dictionary setObject:value forKey:name];
    }
    return [NSString stringWithFormat:@"<%@: %p> -- %@",[self class],self,dictionary];
}
@end

大功告成,此时你可能还会有一个问题,如果你不想打印这个模型的属性,但是由于你重写了description方法,所以每次打印就会看到一大堆烦人的log了,这时又该怎么办?其实苹果还是考虑的很周全的,除了提供description方法以外,它还提供了一个方法用于重写:- (NSString *)debugDescription {},通过重写这个方法,我们就可以解决上面的问题了。不过再写代码之前还是说下原理吧

什么是debugDescription?

其实debugDescription和description是一样的效果. 只不过唯一的区别就是debugDescription是在Xcode控制台里使用po命令的时候调用的,而debugDescription的实现其实也就是调用了description方法而已, 在开发过程中调试的时候,通过重写debugDescription方法就可以了,代码如下:

- (NSString *)debugDescription {
    
     NSMutableDictionary *dictionary = [NSMutableDictionary dictionary];
    
    // 获取当前类的所有属性
    unsigned int count;// 记录属性个数
    objc_property_t *properties = class_copyPropertyList([self class], &count);
    for (int i = 0; i < count; i++) {
        
        // An opaque type that represents an Objective-C declared property.
        // objc_property_t 属性类型
        objc_property_t property = properties[i];
        // 获取属性的名称 C语言字符串
        const char *cName = property_getName(property);
        // 转换为Objective C 字符串
        NSString *name = [NSString stringWithCString:cName encoding:NSUTF8StringEncoding];

        id value = [self valueForKey:name]?:@"nil"; [dictionary setObject:value forKey:name];
        
         [dictionary setObject:value forKey:name];
    }
    return [NSString stringWithFormat:@"<%@: %p> -- %@",[self class],self,dictionary];
    
}

搞定收工!希望能帮到各位小伙伴..

上一篇下一篇

猜你喜欢

热点阅读