美文网首页
关于对象与内存分析总结笔记

关于对象与内存分析总结笔记

作者: GY1994 | 来源:发表于2018-12-02 23:32 被阅读43次

    (一)OC对象在底层中的布局

    我们平时编写的Objective-C代码,在底层都是使用C/C++实现。
    Objective-C -> C/C++ -> 汇编语言 -> 机器语言
    我们定义个NSObject对象

    NSObject *object = [[NSObject alloc] init];
    

    使用终端命令将OC代码转换成iOS能支持的C/C++代码;

    xcrun  -sdk  iphoneos  clang  -arch  arm64  -rewrite-objc  'OC源文件'  -o  '输出的CPP文件'
    

    通过阅读转换后的.cpp文件,可以找到一个名为 NSObject_IMPL的结构体。分析结构体名字实际含义是 NSObject Implementation

    struct NSObject_IMPL {
        Class isa; 
    };
    

    因此我们可以知道OC对象在底层的布局是一个结构体

    (二)对象在内存中的占用大小

    引入<objc/runtime.h>, 使用 class_getInstanceSize方法可获取NSObject实例对象的 成员变量 所占用的大小,可以观察到返回 8 个字节

    class_getInstanceSize([NSObject class])
    

    引入<malloc/malloc.h>, 使用malloc_size方法获取指针所指向的内存大小,可以观察到返回16个字节。

    malloc_size((__bridge const void *)(object));
    

    通过阅读Objc源码 可得知在alloc一个对象时,CoreFunction框架硬性规定分配内存空间不小于16个字节

    1.png
    总结:
    系统分配了16个字节给NSObject对象(通过malloc_size函数获得),但NSObject对象内部只使用了8个字节的空间(64bit环境下,可以通过class_getInstanceSize函数获得)

    (三)通过XCode工具分析内存

    首先打印NSObject对象地址,通过工具ViewMemory查看。
    可观察到前16个字节中,只有8个字节存在数据(存放isa指针)

    2.png

    (四)自定义类内存分析

    定义Student类,初始化。通过重复之前步骤,可观察到底层实现。

    struct Student_IMPL {
        Class isa;
        int _no;
        int _age;
    };
    @interface Student : NSObject
    {
        @public
        int _no;
        int _age;
    }
    @end
    @implementation Student
    @end
    int main(int argc, const char * argv[]) {
        @autoreleasepool {
            Student *stu = [[Student alloc] init];
            stu->_no = 4;
            stu->_age = 5;
            
            NSLog(@"%zd", class_getInstanceSize([Student class]));
            NSLog(@"%zd", malloc_size((__bridge const void *)stu));
        }
        return 0;
    }
    
    

    通过使用class_getInstanceSizemalloc_size方法可观察到占用16个字节存储空间。

    3.png
    使用ViewMemory查看前8个字节存放isa_no_age分别占用4个字节。

    我们也可以使用LLDB指令打印相关地址信息,并且可使用memory write指令直接修改内存中的数据

    4.png
    可以观察到将_no中的值修改为了8

    (五)继承类的内存占用分析

    @interface Person : NSObject
    {
        @public
        int _age;
    }
    @end
    
    @implementation Person
    
    @end
    
    @interface Student : Person
    {
        int _no;
    }
    @end
    
    @implementation Student
    
    @end
    

    分析:Person类中isa指针占用8个字节,_age占用4个字节。通过CoreFunction框架硬性规定分配内存空间不小于16个字节。得知共占用16个字节。
    但是即使无此硬性规定,通过内存对齐规则:结构体的最终大小,必须是最大成员的倍数。

    Student类占用16个字节。isa占用8个字节,_age占用4个字节,剩余4个字节,被_no占用。

    相关文章

      网友评论

          本文标题:关于对象与内存分析总结笔记

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