美文网首页
iOS中的内存对齐(修改版)

iOS中的内存对齐(修改版)

作者: 白鹭上晴天 | 来源:发表于2019-06-11 15:01 被阅读0次

    一、什么是内存对齐
    内存对齐是一种在计算机内存中排列数据(表现为变量的地址)、访问数据(表现为CPU读取数据)的一种方式。

    它包含了两种相互独立又相互关联的部分:基本数据对齐和结构体数据对齐 。

    二、为什么我们要进行内存对齐?
    1、平台原因(移植原因):不是所有的硬件平台都能访问任意地址上的任意数据的;某些硬件平台只能在某些地址处取某些特定类型的数据,否则抛出硬件异常。

    2、性能原因:数据结构(尤其是栈)应该尽可能地在自然边界上对齐。原因在于,为了访问未对齐的内存,处理器需要作两次内存访问;而对齐的内存访问仅需要一次访问。

    三、iOS中实例对象的本质
    首先举个例子,我们来以ZXClass进行研究

    @interface ZXClass : NSObject
    {    
        int time;
    }
    @end
    
    @implementation ZXClass
        ZXClass *obj = [[ZXClass alloc] init];
    @end
    

    接下来我们分别使用

    class_getInstanceSize([ZXClass class])
    malloc_size((__bridge const void *)obj)
    

    进行打印操作,答应出来的结果分别是12和16,为什么打印出来的结果会有所不同呢。

    接下来我们先对于ZXClass进行分析,在iOS中实例对象相当于是一个结构体,我们将刚刚所写的代码通过终端敲入

    clang -rewrite-objc main.m -o  main.cpp
    

    指令后,生成如下代码

    struct ZXClass_IMPL {
        struct NSObject_IMPL NSObject_IVARS;
        int time; // 4个字节
    };
    
    structNSObject_IMPL {
        Class isa; // 8个字节
    };
    

    根据上面生成的个结构体可以直观的看出一个ZXClass在内存中所占用的大小应该是4Byte(int) + 8Byte(isa) = 12Byte,这么看出来之前getInstanceSize方法所打印出来的结果应该是正确的,为什么会出现malloc_size的16结果呢?

    这里就牵扯到iOS中的内存对齐这个概念了。

    四、iOS中所运用的内存对齐
    带着上面的问题,我们打开苹果开源下载网站(https://opensource.apple.com/tarballs/libmalloc/)进行下载

    在 nano_malloc.c中我们可以找到很多关于内存分配的判断函数,根据分析,最后得出一个结论iOS中对于内存分配有对齐的概念,也就是说所分配的内存空间要满足以下两个条件:

    1⃣️所分配的内存空间要大于等于对象所真正需要占用的内存空间

    2⃣️所分配的内存空间必须要是16*n的结构

    这样,我们再反过头来看上面的这个问题,ZXClass中定义了一个int 类型的变量所占内存为4Byte 一个继承自父类NSOjbect的isa所占内存为8Byte,所以真实需要的内存地址为12Byte,又因为第二点规定,所以内存分配的空间为16Byte.

    也就是说系统给ZXClass分配了16个字节,而它本身只占用了12个字节,剩下4个为空。

    了解这些规律以后,在今后的开发中要尽可能的去进行优化

    相关文章

      网友评论

          本文标题:iOS中的内存对齐(修改版)

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