OC:对象的isa指针和superclass指针分别指向哪里,你知道了吗?

简介: OC:对象的isa指针和superclass指针

一、isa指针

0398da01882f4040a161586152d3cf58.png


# if __arm64__
#   define ISA_MASK        0x0000000ffffffff8ULL
# elif __x86_64__
#   define ISA_MASK        0x00007ffffffffff8ULL
#endif

1、instance对象(实力对象)的 isa 指向class对象。

2、当调用对象方法时,通过instance的 isa 找到class,最后找到对象方法的实现进行调用。

3、class对象的 isa 指向 meta-class对象

4、当调用类方法时,通过class的 isa 找到meta-class,最后找到类方法的实现进行调用。

5、从64bit开始,isa 需要进行一次位运算,才能计算出真实地址。


二、class对象的superclass指针


创建两个类,以下示例下文通用:


@interface Person : NSObject
@end
@implementation Person
@end
@interface Student : Person
@end
@implementation Student
@end


那么它们之间的ce4a69fb069248368b1b61c5283ff82c.png superclass 指针的指向关系如下:



当Student的instance对象要调用Person的对象方法时,会先通过 isa 找到Student的class,然后通过 superclass 找到Person的class,最后找到对象方法的实现进行调用。


三、meta-class对象的superclass指针

b240a2e2dc6b4339afc434b39237c358.png

当Student的class要调用Person的类方法时,会先通过isa找到Student的meta-class,然后通过superclass找到Person的meta-class,最后找到类方法的实现进行调用


四、isa,superclass一览


这是一张来自大佬的关于解释 isa、superclass 的流程图:

eb68dabba8264c43b70fefcbfbdd3648.png

引用上面的代码示例分析如下:

b97a4bbc9f20443d8c1e54afc99018f6.png


结论:


instance对象的 isa 指向class对象。

class对象的 isa 指向meta-class对象

meta-class对象的 isa 指向基类的meta-class对象

class对象的 superclass 指向父类的class对象,如果没有父类,superclass指针为nil。

meta-class对象的 superclass 指向父类的meta-class对象

基类的meta-class对象的 superclass 指向基类的class对象

instance对象调用对象方法的轨迹:

isa 找到class,方法不存在,就通过 superclass 找父类,直到知道为止。

class对象调用类方法的轨迹:

isa找meta-class对象,方法不存在,就通过 superclass 找父类,一直找到基类的meta-class对象,如果还没有找到,继续通过 superclass 指向基类的class对象。直到找到为止。


五、struct objc_class结构分析

476bb90dcefb4d82b5c65de1b9cef449.png

class对象、meta-class对象的本质结构都是struct objc_class。其底层实现如下图:

d50380ded88044f1bec95bd41139c9ff.png

添加数据指针偏移量:


#if !__LP64__
#define FAST_DATA_MASK        0xfffffffcUL
#elif 1
#define FAST_DATA_MASK          0x00007ffffffffff8UL
#else
#define FAST_DATA_MASK          0x00007ffffffffff8UL
#endif


拓展

1、OC对象的 isa 指针指向哪里?


1、instance对象的isa指向class对象。

2、class对象的isa指向meta-class对象。

3、meta-class对象的isa指向基类的meta-class对象。


相关文章
|
5月前
|
存储 C++
C++程序中的对象指针
C++程序中的对象指针
37 1
|
2月前
|
编译器 C++
virtual类的使用方法问题之在C++中获取对象的vptr(虚拟表指针)如何解决
virtual类的使用方法问题之在C++中获取对象的vptr(虚拟表指针)如何解决
|
4月前
|
编译器 C++
函数指针和函数对象不是同一类型怎么替换
函数指针和函数对象不是同一类型,为何可替换用作同一函数的参数
|
4月前
|
算法 Java 程序员
面向对象编程(OOP)通过对象组合构建软件,C语言虽是过程式语言,但可通过结构体、函数指针模拟OOP特性
【6月更文挑战第15天】面向对象编程(OOP)通过对象组合构建软件,C语言虽是过程式语言,但可通过结构体、函数指针模拟OOP特性。封装可使用结构体封装数据和方法,如模拟矩形对象。继承则通过结构体嵌套实现静态继承。多态可通过函数指针模拟,但C不支持虚函数表,实现复杂。C语言能体现OOP思想,但不如C++、Java等语言原生支持。
54 7
|
4月前
类与对象\this指针
类与对象\this指针
25 0
|
4月前
|
C++
【C++系列】指针对象和对象指针的区别
这段内容介绍了C++中`ListNode`对象和指针的两种使用方式以及它们的区别。首先,`ListNode dummy(0); ListNode* cur = &dummy;创建了一个`ListNode`对象`dummy`在栈上,`cur`是`dummy`的地址。而`ListNode* dummy = new ListNode(0); ListNode* cur = dummy;`则在堆上分配了一个`ListNode`,`dummy`和`cur`都是指向该对象的指针。使用`&dummy`作为虚拟头节点简化链表操作,避免特殊处理。栈分配内存自动管理但生命周期受限,堆分配内存需手动释放且速度较慢。
|
4月前
|
存储 安全 编译器
C++进阶之路:探索访问限定符、封装与this指针的奥秘(类与对象_上篇)
C++进阶之路:探索访问限定符、封装与this指针的奥秘(类与对象_上篇)
31 0
|
5月前
|
存储 编译器 程序员
从C语言到C++④(第二章_类和对象_上篇)->类->封装->this指针(下)
从C语言到C++④(第二章_类和对象_上篇)->类->封装->this指针
22 0
|
5月前
|
存储 编译器 C语言
从C语言到C++④(第二章_类和对象_上篇)->类->封装->this指针(中)
从C语言到C++④(第二章_类和对象_上篇)->类->封装->this指针
25 0
|
5月前
|
Java C语言 C++
从C语言到C++④(第二章_类和对象_上篇)->类->封装->this指针(上)
从C语言到C++④(第二章_类和对象_上篇)->类->封装->this指针
34 0