美文网首页iOS底层基础知识iOS面试知识点
iOS-底层原理(3.5)-isa-Class的结构详解

iOS-底层原理(3.5)-isa-Class的结构详解

作者: 路飞_Luck | 来源:发表于2018-08-25 22:51 被阅读71次
isa指针图解
image.png

代码例子佐证 - 实例对象isa验证

#import <Foundation/Foundation.h>
#import <objc/runtime.h>

// MJPerson
@interface CSPerson : NSObject {
@public
    int _age;
}
@property (nonatomic, assign) int no;
- (void)personInstanceMethod;
+ (void)personClassMethod;
@end

@implementation CSPerson
- (void)test {
}
- (void)personInstanceMethod {
}
+ (void)personClassMethod {
}
@end

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        // CSPerson类对象的地址:0x0000000100001240
        // CSPerson实例对象的isa:0x001d800100001241
        // isa(0x001d800100001241) & ISA_MASK(0x0000000ffffffff8):0x0000000100001240
        
        CSPerson *person = [[CSPerson alloc] init];
        
        Class personClass = [CSPerson class];
        
        Class personMetaClass = object_getClass(personClass);
        
        NSLog(@"%p %p %p", person, personClass, personMetaClass);
    }
    return 0;
}

打印结果

image.png

从打印结果我们可以知道实例对象的isa指针 & ISA_MASK等于类对象的地址

代码例子佐证 - 类对象isa验证
CSPerson代码还是使用上述代码,只是增加一个结构体

struct cs_objc_class {
    Class isa;
};
int main(int argc, const char * argv[]) {
    @autoreleasepool {
        // CSPerson类对象的地址:0x001d800100001219
        // CSPerson元类对象的地址: 0x0000000100001218
        // isa(0x001d800100001219) & ISA_MASK(0x0000000ffffffff8) = 0x0000000100001218
       
        Class personClass = [CSPerson class];
        
        struct cs_objc_class *personClass2 = (__bridge struct cs_objc_class *)(personClass);
        
        Class personMetaClass = object_getClass(personClass);
        
        NSLog(@"%p %p %p", person, personClass, personMetaClass);
    }
    return 0;
}

输出结果

image.png

从打印结果我们可以知道类对象的isa指针 & ISA_MASK等于元类对象的地址

superclass

代码例子佐证 - 新增CSStudent类,cs_objc_class结构体

// CSStudent
@interface CSStudent : CSPerson {
@public
    int _weight;
}
@property (nonatomic, assign) int height;
- (void)studentInstanceMethod;
+ (void)studentClassMethod;
@end

@implementation CSStudent
- (void)test{
}
- (void)studentInstanceMethod{
}
+ (void)studentClassMethod{
}
@end

struct cs_objc_class {
    Class isa;
    Class superclass;
};

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        // 3. superclass
        struct cs_objc_class *personClass = (__bridge struct cs_objc_class *)([CSPerson class]);
        struct cs_objc_class *studentClass = (__bridge struct cs_objc_class *)([CSStudent class]);
        
        NSLog(@"%p %p", personClass, studentClass);
    }
    return 0;
}

运行结果

image.png

从打印结果可知,类对象的superclass指向元类对象地址

项目连接地址 - Isa-class-detail

struct objc_class

image.png
  • class、meta-class对象的本质结构都是struct objc_class

窥探struct objc_class的结构

image.png

代码佐证
引入#import "MJClassInfo.h"文件,然后编写类

#import <Foundation/Foundation.h>
#import <objc/runtime.h>
#import "MJClassInfo.h"

// CSPerson
@interface CSPerson : NSObject {
@public
    int _age;
}
@property (nonatomic, assign) int no;
- (void)personInstanceMethod;
+ (void)personClassMethod;
@end

@implementation CSPerson
- (void)test {
}
- (void)personInstanceMethod {
}
+ (void)personClassMethod {
}
@end

// CSStudent
@interface CSStudent : CSPerson {
@public
    int _weight;
}
@property (nonatomic, assign) int height;
- (void)studentInstanceMethod;
+ (void)studentClassMethod;
@end

@implementation CSStudent
- (void)test{
}
- (void)studentInstanceMethod{
}
+ (void)studentClassMethod{
}
@end

int main(int argc, const char * argv[]) {
    @autoreleasepool {
        CSStudent *stu = [[CSStudent alloc] init];
        stu->_weight = 10;
        
        mj_objc_class *studentClass = (__bridge mj_objc_class *)([CSStudent class]);
        mj_objc_class *personClass = (__bridge mj_objc_class *)([CSStudent class]);
        
        class_rw_t *studentClassData = studentClass->data();
        class_rw_t *personClassData = personClass->data();
        
        class_rw_t *studentMetaClassData = studentClass->metaClass()->data();
        class_rw_t *personMetaClassData = personClass->metaClass()->data();
        
        NSLog(@"1111");
    }
    return 0;
}

运行结果分析

  • mj_objc_class结构
mj_objc_class.png
  • 类对象mj_objc_class结构
image.png
  • 元类对象mj_objc_class结构
meta_mj_objc_class.png

面试题

1.对象的isa指针指向哪里?
  • instance对象的isa指向class对象
  • class对象的isa指向meta-class对象
  • meta-class对象的isa指向基类的meta-class对象
2.OC的类信息存放在哪里?
  • 对象方法、属性、成员变量、协议信息,存放在class对象中
  • 类方法,存放在meta-class对象中
  • 成员变量的具体值,存放在instance对象

本文参考借鉴MJ的教程视频,非常感谢


项目连接地址 - isa-class-struct

相关文章

网友评论

    本文标题:iOS-底层原理(3.5)-isa-Class的结构详解

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