C++随手记 - 编译与内存相关

一、编译与内存相关

A、编译与链接

1、编译过程:

  • 编译预处理:引入头文件、去注释、处理所有的条件编译指令、宏替换等
  • 编译:词法分析、语法分析、语义分析、汇编代码生成,并对程序进行优化,最终将.cpp文件翻译成.s的汇编代码
  • 汇编:将.s翻译成机器指令.o文件
  • 链接:一个程序可能由多个源文件组成,此时存在多个.o文件。A文件的函数调用B文件的变量,就需要链接成一个整体。

2、静态链接和动态链接

  • 静态链接:代码在生成可执行文件时,将该程序所需要的全部外部调用函数拷贝到最终可执行文件中,该程序被执行时,运行所需要的全部代码都会被装入到进程虚拟地址空间。静态链接库一般以.a文件,可以将多个.o文件连接成一个静态链接库。
  • 动态链接:

B、变量

1、作用域

  • 全局变量:全局作用域。只需定义一次,其他文件想要使用需要extern关键字再次声明。
  • 静态全局变量:文件作用域。不能被extern修饰,即使两个文件定义了同名的静态全局变量,他们也是不同变量
  • 局部变量:局部作用域。以{}为作用域,对作用域外不可见。函数执行结束后,变量被撤销,占用的空间也被收回
  • 静态局部变量:局部作用与。只被初始化一次,一直到程序运行结束都存在,但只对作用域内可见

C、内存对齐

1、CPU在读取内存时不是以字节为单位,而是以机器字长为单位,实际机器字长由CPU总线宽度决定。比如32位CPU,机器字长4字节,数据总线宽度32位,如果该CPU地址总线宽度也是32位,则其可以方位的地址空间为[0,0xFFFFFFFF]。内存对齐可以:

  • 减少CPU访问内存的次数,加大CPU访问内存的吞吐量。
  • 某些特定硬件设备只能存取对齐数据,比如CPU中的SIMD,要求内存严格对齐

2、内存对齐的原则

  • 结构体变量首地址能够被其最宽的基本类型成员的长度和对齐基数二者中的较小者整除
  • 结构体中的static成员变量不占用结构体的空间。因为静态成员变量在程序初始化时就已经在静态存储区分配完成,所有该结构体实例中的静态成员都指向同一个内存区域。
struct st{
	char a;
	int b;
	static double c; // 静态成员
}
cout << sizeof(st) << endl; // 8
  • 结构体每个成员相对于结构体首地址的偏移量都是该成员大小与对齐基数的较小者的整数倍,如有需要,编译器会在成员间加上填充字节
  • 结构体的总大小为结构体中最宽的基本类型成员长度和对齐基数二者中的较小者的整数倍,如有需要,编译器会在最末尾的成员之后加上填充字节

3、指定程序对齐

#pragma pack (x) // 以x的字节单位对齐
struct st{
	.......
}
#pragma pack()
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值