zoukankan      html  css  js  c++  java
  • struct内存对齐

    内存对齐其实是为了在程序运行的时候更快的查找内存而做的一种编译器优化。

     

    我们先看这样一个例子:

     1 #include <iostream>
     2 using namespace std;
     3 
     4 struct vpoet
     5 {
     6     int a;   //4 bytes
     7     char b;   //1 bytes
     8     double c;  // 8 bytes
     9     char *d;   //4 bytes
    10     int e;     //4 bytes
    11 };
    12 
    13 int main()
    14 {
    15     cout<<"sizeof(vpoet)="<<sizeof(vpoet)<<endl;
    16     return 0;
    17 }

    运行结果:

    这个结构体大小为24个字节,但是我们仔细算一算其字节数发现其实际上只有4+1+8+4+4=21个字节,那是如何算出来24个字节的

    呢,其实在默认情况下编译器是按照结构体中所占字节最大的成员来进行内存对齐的。比如在结构体vpoet中最大的是double double

    占8个字节,那么编译器默认按8个字节的方式对齐那么编译器将按照大于实际字节数的double最小整数倍来进行内存分配。因而这里

    实际是在结构体的成员b后面填充了三个字节用于对齐。

    那么问题来了,对齐方式可以改吗?可以我们可以在文件头加上

    1 #pragma pack(n)

    来改变内存对齐的字节数

     

    比如当我们按照一个字节对齐的时候:

     1 #include <iostream>
     2 using namespace std;
     3 #pragma pack(1)
     4 
     5 struct vpoet
     6 {
     7     int a;   //4 bytes
     8     char b;   //1 bytes
     9     double c;  // 8 bytes
    10     char *d;   //4 bytes
    11     int e;     //4 bytes
    12 };
    13 
    14 int main()
    15 {
    16     cout<<"sizeof(vpoet)="<<sizeof(vpoet)<<endl;
    17     return 0;
    18 }

    运行结果:

    当我们按照1字节对齐的时候,编译器将为该结构体分配本身实际大小的字节数

     

    当我们以2字节对齐的时候

    1 #pragma pack(2)

    此时的输出结果为:

    当我们按照2字节对齐的时候,编译器将为结构体成员b后面填充一个空字节用于内存对齐。

    记住这样一个规律:

    默认情况下编译器将按照实际结构体中占内存字节数最大的成员的整数倍进行分配,该最大的整数倍应正好大于或者等于结构

    体实际所占的内存字节数

  • 相关阅读:
    WSL中使用npm install报错
    在npm install时node-gyp出现错误
    Chrome禁用隐藏www和m
    Git始终忽略特定文件的某一行内容
    macOS关闭修改扩展名的提示
    解决安装Anaconda后ZSH中使用的依然是系统自带的Python
    macOS上更顺手的终端
    自用的越狱插件
    Tomcat安装后修改路径方法
    TestStack.White安装详解
  • 原文地址:https://www.cnblogs.com/vpoet/p/4679900.html
Copyright © 2011-2022 走看看