zoukankan      html  css  js  c++  java
  • runtime 理解笔记

    runtime 简称运行时,是系统运行的一种机制,在oc中通过c语言编写一个运行系统库。考进行一些非常底层的操作(oc无法完成的)。

    1、利用runtime,在程序运行过程中,动态创建一个类(比如KVO)。

    2、利用runtime, 在程序运行过程中,动态的修改一个类的属性方法,添加属性方法。

    3、遍历一个类的所有成员变量。(字典转模型)

    4、

    对runtime要深入理解,首先需要理解 isa,  objc_object, objc_class

    在 Objective-C 中,类、对象和方法都是一个 C 的结构体,从 objc/objc.h(对象,objc_objectid)以及objc/runtime.h(其它,类,方法,方法列表,变量列表,属性列表等相关的)以及中,我们可以找到他们的定义。

    isa指针是和Class同类型的objc_class结构指针,类对象的指针指向其所属的类,即元类。元类中存储着类对象的类方法,当访问某个类的类方法时会通过该isa指针从元类中寻找方法对应的函数指针。

    对象与类的关系

    objc.h :  objc_object

    /// Represents an instance of a class.
    struct objc_object {
        Class _Nonnull isa  OBJC_ISA_AVAILABILITY;
    };

    runtime.h :  objc_class 

    struct objc_class {
        Class _Nonnull isa  OBJC_ISA_AVAILABILITY;
    
    #if !__OBJC2__
        Class _Nullable super_class                              OBJC2_UNAVAILABLE;
        const char * _Nonnull name                               OBJC2_UNAVAILABLE;
        long version                                             OBJC2_UNAVAILABLE;
        long info                                                OBJC2_UNAVAILABLE;
        long instance_size                                       OBJC2_UNAVAILABLE;
        struct objc_ivar_list * _Nullable ivars                  OBJC2_UNAVAILABLE;
        struct objc_method_list * _Nullable * _Nullable methodLists                    OBJC2_UNAVAILABLE;
        struct objc_cache * _Nonnull cache                       OBJC2_UNAVAILABLE;
        struct objc_protocol_list * _Nullable protocols          OBJC2_UNAVAILABLE;
    #endif
    
    } OBJC2_UNAVAILABLE;
    /* Use `Class` instead of `struct objc_class *` */

    说明:

    1、对象是一个objc_object的结构体,类是一个objc_class的结构体.

    2、对象的isa指向对象类本身,包含了当前对象指向的类的信息;  类的isa指向元类,包含了类对象指向的元类(meta-class)的信息。

    3、NSObject类中包含的是一个objc_class结构体类型的isa,指向该对象对应的类。

    元类(metaClass)

    元类(Metaclass)就是类对象,每个都有自己的元类,也就是objc_class结构体里面isa指针所指向的类. Objective-C的类方法是使用元类的根本原因,因为其中存储着对应的类对象调用的方法即类方法

    当向对象发消息,runtime会在这个对象所属类方法列表中查找发送消息对应的方法,但当向类发送消息时,runtime就会在这个类的meta class方法列表里查找。所有的meta class,包括Root class,Superclass,Subclass的isa都指向Root class的meta class,这样能够形成一个闭环。

    结构图:

    所以由上图可以看到,在给实例对象或类对象发送消息时,寻找方法列表的规则为:

    • 当发送消息给实例对象时,消息是在寻找这个对象的类的方法列表(实例方法)
    • 当发送消息给类对象时,消息是在寻找这个类的元类的方法列表(类方法)

    元类,就像之前的类一样,它也是一个对象,也可以调用它的方法。所以这就意味着它必须也有一个类。所有的元类都使用根元类作为他们的类。比如所有NSObject的子类的元类都会以NSObject的元类作为他们的类。

    根据这个规则,所有的元类使用根元类作为他们的类,根元类的元类则就是它自己。也就是说基类的元类的isa指针指向他自己。

    技巧:

    1、#import <objc/message.h> 包含了 #include <objc/objc.h>, #include <objc/runtime.h>

    #ifndef _OBJC_MESSAGE_H
    #define _OBJC_MESSAGE_H
    
    #include <objc/objc.h>
    #include <objc/runtime.h>
    
    #ifndef OBJC_SUPER
    #define OBJC_SUPER
  • 相关阅读:
    TCP—为什么是AIMD?
    虚拟机是怎么实现的?
    漫谈linux文件IO
    关于大型网站技术演进的思考
    大公司里怎样开发和部署前端代码
    spawn-fcgi 代码介绍
    使用python传参form-data格式的txt请求接口
    实战scrapy抓取站长图片数据
    通过requests和lxml模块对网站数据进行爬取
    centos7.5下安装jenkins
  • 原文地址:https://www.cnblogs.com/xujinzhong/p/11309528.html
Copyright © 2011-2022 走看看