美文网首页
关于Runtime学习的个人见解

关于Runtime学习的个人见解

作者: 0143fc60fe45 | 来源:发表于2016-03-10 15:20 被阅读58次

一年多的iOS开发经验,也学习了一些有关Runtime的知识,在这里写下自己的一点小心德。

学习runtime个人认为主要理解两点:1.类(对象)的底层实现    2.OC的消息机制


runtime是C语言写的,OC中的类在runtime中都转变成结构体表示。

在OC中NSObject为基类,找到NSObject.h文件中NSObject的定义:

@interface NSObject {

    Class isa OBJC_ISA_AVAILABILITY;

}

我们可以看到基类中有一个名为isa的成员变量,isa其实是一个指向objc_class的结构体指针。按住Command键,点击进入,来到objc_class的定义(同时你会发现来到runtime.h中):

struct objc_class {

Class isa OBJC_ISA_AVAILABILITY;

#if !__OBJC2__

Class super_class                                                      OBJC2_UNAVAILABLE;

const char *name                                                      OBJC2_UNAVAILABLE;

long version                                                                OBJC2_UNAVAILABLE;

long info                                                                       OBJC2_UNAVAILABLE;

long instance_size                                                      OBJC2_UNAVAILABLE;

struct objc_ivar_list *ivars                                        OBJC2_UNAVAILABLE;

struct objc_method_list **methodLists                  OBJC2_UNAVAILABLE;

struct objc_cache *cache                                             OBJC2_UNAVAILABLE;

struct objc_protocol_list *protocols                          OBJC2_UNAVAILABLE;

#endif

} OBJC2_UNAVAILABLE;

当我们创建obj时,每个obj中都有一个isa指针,指向自己的类的结构体。接下来讲解下这个结构体主要的成员:

1.isa指针:obj中的isa指向类的结构体,而类的结构体中的isa又指向谁呢?其实isa指向元类metaclass。

2.super_class指针:指向类的父类。(下面盗用一张图帮助理解,继承之间两种指针的指向)

isa指针和superclass指针的指向图

3.ivars:类的成员变量列表指针,用于存放类的成员变量。

4.methodLists:类的方法列表指针,用于存放类的方法列表。

PS:这里同学们自己在runtime.h中搜索下这几个结构体的构成,理解了会有大帮助。

类的其他成员就不一一列举了。


第2点:OC的消息机制。

参考:http://blog.jobbole.com/79574/

在开始前,同学们应该先了解SEL、IMP、Method三者间的关系。

当obj或者class调用一个方法时(相当于往obj或class发送一个SEL),会先找到isa指针指向的metaClass,然后在metaClass中找到methodLists,从methodLists中根据SEL找到相应的IMP,并执行IMP。如果找不到,则从superClass中找,直到rootClass中还找不到相应的IMP,则系统会进行以下三个步骤:

1.如果一直找不到IMP,调用+ (BOOL)resolveInstanceMethod:方法,返回NO告诉系统找不到IMP。

2.调用- (id)forwardingTargetForSelector:方法返回一个对象,将消息转发到该对象(默认应该是返回nil对象)。

3.如果转发对象中也找不SEL相应的IMP,系统会调用- (NSMethodSignature *)methodSignatureForSelector:方法返回一个NSMethodSignature对象(默认应该为nil),系统根据NSMethodSignature对象,创建一个NSInvocation对象,然后调用- (void)forwardInvocation:方法(forwardInvocation默认调用- (void)doesNotRecognizeSelector:抛出异常)。

了解到OC的消息机制后,说说我们可以在这个机制中做什么?

1.在调用+ (BOOL)resolveInstanceMethod:时,可以这里动态地为SEL往Method中添加IMP,并返回YES,可以防止程序的崩溃。 

2.在调用- (id)forwardingTargetForSelector:时可以返回一个拥有SEL对应的IMP的obj,这样使原来的obj在没有继承拥有该IMP类的情况下可以使用该SEL,变相地使OC有多继承的效果。

3.重写- (NSMethodSignature *)methodSignatureForSelector:和- (void)forwardInvocation:方法,重SEL转发给一个拥有相应IMP的obj。

以上三种做法,可以在参考中找到具体实现。其中1的原理是动态添加IMP,2和3原理都是把消息转发到一个有相应IMP的obj。


到这里,同学们对OC的底层实现,runtime应该有一个更好的了解了。相信了解了构造后,再来理解功能就变得简单些啦。

打开runtime.h文件,点击selection列表,我们可以总体的浏览下runtime的方法和定义,定义呢主要就是我们上面讲的底层实现结构,而这里的方法主要有object、objc、class、ivar、sel、imp和method这些开头。从方法名开头可以看出,主要是对对象、类、属性、方法选择器、方法实现和方法的操作。


以上是我学习runtime的方法和一些小心得,希望对同学们有帮助。

最后,希望大家指点出不足与错误之处。

相关文章

  • 关于Runtime学习的个人见解

    一年多的iOS开发经验,也学习了一些有关Runtime的知识,在这里写下自己的一点小心德。 学习runtime个人...

  • runtime个人见解

    Runtime简称运行时,OC就是运行时机制,也就是运行时候的一些机制,其中最重要的就是 消息机制。 对于C语言,...

  • iOS runtime 的个人见解

    runtime是一个iOS开发必须要了解的一个特别厉害的技术, 以前总是认为靠近底层的东西在实际中并不实用, 可是...

  • 关于runtime的学习笔记

    runtime简称运行时,就是系统在运行的时候的一些机制,其中最主要的是消息机制。常见的作用:动态的添加对象的成员...

  • Runtime

    从同事给的一个关于runtime的.html文件复制过来的留着学习,还有没写到的后面再添加整理 一、runtime...

  • swift runtime

    关于 runtime

  • 中文版-Objective-C Runtime Programm

    前言 Runtime是iOS开发者进阶必须学习的一个知识点。网上关于Runtime 有许多介绍,有深入有简单介绍,...

  • 关于Objective-C Runtime看我就够了

    前言 Runtime是iOS开发者进阶必须学习的一个知识点。网上关于Runtime 有许多介绍,有深入有简单介绍,...

  • Objective-C Runtime [收藏]

    前言 Runtime是iOS开发者进阶必须学习的一个知识点。网上关于Runtime 有许多介绍,有深入有简单介绍,...

  • iOS中Runtime的常用方法

    Runtime是什么? Apple关于Runtime的详细文档链接:Runtime Guide其实大家对Runti...

网友评论

      本文标题:关于Runtime学习的个人见解

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