美文网首页
iOS关于hook所有界面后提升初始化速度的方案

iOS关于hook所有界面后提升初始化速度的方案

作者: 陌路问途 | 来源:发表于2017-05-15 14:37 被阅读220次

    因为某些业务需求,项目需要hook所有界面的viewDidAppear方法,我们的方案是使用runtime获取系统所有的类然后将其替换成我们的方法,但是使用这个方法后,在比较小的项目中没什么问题,速度慢的400ms左右,但是在比较大的项目中就严重影响了初始化的速度,在使用了Instruments监测速度的工具后,发现占时比较多的是下面这个方法:

    unsignedintoutCount =0;
    //这个方法是耗时大户
    Class *classLiset = objc_copyClassList(&outCount);
    //遍历也是耗时大户
    for(unsignedinti =0; i < outCount; i++) {
    
    if([UIViewController Class] == class_getSuperclass(classLiset[i])){
        //对抓到的类进行hook
    }
    
    free(classLiset);
    

    我们发现 objc_copyClassList(&outCount)方法会获取到系统中的所有类,就算是对初始项目使用这个方法他也能获取到16000个左右的类,而获取到这个16000个类之后对他进行遍历,也就造成了非常严重的耗时,更别说复杂一些的项目了。所以,为了解决这个问题,一开始能想到的方法就是提升遍历的速度,不使用这个普通的for循环,而是使用forin的方法来增强遍历的速度,可是我们发现,这个Class类型是个结构体,不是forin可以遍历的类型,于是乎便放弃了这个想法。

    既然没法对遍历进行提速,那么我们需要提速的对象就自然而然的是 objc_copyClassList(&outCount)获取所有类的方法了,回顾我们的需求,是获取所有控制器,之后替换他们的viewDidAppear方法,那么,我们用objc_copyClassList(&outCount)获取系统的所有类是否是获取太多了呢?毕竟,我们需要的也就是我们用到的一些类,而用了这个方法,不管用没用到,系统中的所有类都会被抓到,于是,我就在想,有没可以获取自己创建的类的方法,毕竟比起获取系统类的最少16000的量级,获取自己的类就会少非常多,于是乎google了一下,还真的找到了这样的方法

    #import <dlfcn.h>
    #import <mach-o/ldsyms.h>
    
    unsigned int count;
    const char **classes;
    Dl_info info;
        
    //1.获取app的路径
    dladdr(&_mh_execute_header, &info);
        
    //2.返回当前运行的app的所有类的名字,并传出个数
    //classes:二维数组 存放所有类的列表名称
    //count:所有的类的个数
    classes = objc_copyClassNamesForImage(info.dli_fname, &count);
    
    for (int i = 0; i < count; i++) {
        NSString *className = [NSString stringWithCString:classes[i] encoding:NSUTF8StringEncoding];
          if (![className isEqualToString:@""] && className) {
              Class class = NSClassFromString(className){
              //做些操作
              }
          }
      }
    

    在使用这个方法后,获取的就成了开发者创建出的类,数量少了非常多,方法的耗时减少,后面的遍历也就变的不怎么耗时了,唯一稍微有点耗时的就是 NSString *className = [NSString stringWithCString:classes[i] encoding:NSUTF8StringEncoding]将string转为类的这个方法了,但是比起之前那1S左右的初始化,这个速度已经无伤大雅了~

    相关文章

      网友评论

          本文标题:iOS关于hook所有界面后提升初始化速度的方案

          本文链接:https://www.haomeiwen.com/subject/lklhxxtx.html