ObjC 学习笔记(一):数据结构定义

iOS开发工程中,我们每天都会使用到ObjC,也会用到runtime的很多操作msgSendmethod_swizzlingobjc_setAssociatedObjectobjc_getAssociatedObject等常用的runtime操作,那runtime究竟是怎样实现的呢?我们底层的数据结构又是怎样的呢?带着这些问题,开始学习runtime相关的内容。

源码地址: objc4源代码

我们看到我们最常引入的头文件#import,我们可以看到runtime定义了ObjC的运行时状态,类、属性、方法、协议、拓展等内容的实现。下面我们从类的定义开始阅读。

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;


从上面的代码可以看出来类的定义是以结构的形式实现,包含有类本身及父类的信息,属性列表、方法列表、缓存和协议列表。

objc_ivar

objc_ivar_list定义了属性类的属性列表,在objc_ivar_list包含了一个objc_ivar的一个数组,通过这两个结构实现类的属性存储。

struct objc_ivar {
    char * _Nullable ivar_name                               OBJC2_UNAVAILABLE;
    char * _Nullable ivar_type                               OBJC2_UNAVAILABLE;
    int ivar_offset                                          OBJC2_UNAVAILABLE;
#ifdef __LP64__
    int space                                                OBJC2_UNAVAILABLE;
#endif
}                                                            OBJC2_UNAVAILABLE;

struct objc_ivar_list {
    int ivar_count                                           OBJC2_UNAVAILABLE;
#ifdef __LP64__
    int space                                                OBJC2_UNAVAILABLE;
#endif
    /* variable length structure */
    struct objc_ivar ivar_list[1]                            OBJC2_UNAVAILABLE;
}                                                            OBJC2_UNAVAILABLE;

objc_method

和属性一样objc_method_list中同样包含了一个objc_method的数组,通过这两个方法实现了方法列表。

struct objc_method {
    SEL _Nonnull method_name                                 OBJC2_UNAVAILABLE;
    char * _Nullable method_types                            OBJC2_UNAVAILABLE;
    IMP _Nonnull method_imp                                  OBJC2_UNAVAILABLE;
}                                                            OBJC2_UNAVAILABLE;

struct objc_method_list {
    struct objc_method_list * _Nullable obsolete             OBJC2_UNAVAILABLE;

    int method_count                                         OBJC2_UNAVAILABLE;
#ifdef __LP64__
    int space                                                OBJC2_UNAVAILABLE;
#endif
    /* variable length structure */
    struct objc_method method_list[1]                        OBJC2_UNAVAILABLE;
}                                                            OBJC2_UNAVAILABLE;

Protocol

protocol的实现方式和methodivar类似,他们都有一个objc_protocol_list以及Protocol的数组去实现协议的列表,不同的是Protocol的实现不再是一个结构,而是一个继承自NSObject的类。

struct objc_protocol_list {
    struct objc_protocol_list * _Nullable next;
    long count;
    __unsafe_unretained Protocol * _Nullable list[1];
};

objc_category

category 定义了Category的数据结构,通过category_name区分不同的category,通过class_name关联相关的类。

struct objc_category {
    char * _Nonnull category_name                            OBJC2_UNAVAILABLE;
    char * _Nonnull class_name                               OBJC2_UNAVAILABLE;
    struct objc_method_list * _Nullable instance_methods     OBJC2_UNAVAILABLE;
    struct objc_method_list * _Nullable class_methods        OBJC2_UNAVAILABLE;
    struct objc_protocol_list * _Nullable protocols          OBJC2_UNAVAILABLE;
}                                                            OBJC2_UNAVAILABLE;

如上就是runtime相关的定义。然后一些常用的操作又是怎么实现的呢?我们在进一步的学习其他的相关操作。

更好的阅读体验可以参考个人网站:https://zevwings.com

你可能感兴趣的:(ObjC 学习笔记(一):数据结构定义)