[toc]
# 基础知识
C++ 内存分区:栈、堆、全局 / 静态存储区、常量存储区、代码区
- 栈:存放函数的局部变量、函数参数、返回地址等,由编译器自动分配和释放
- 堆:动态申请的内存空间,就是由
malloc
分配的内存块,由程序员控制它的分配和释放,如果程序执行结束还没有释放,操作系统会自动回收。 - 全局区 / 静态存储区 (.bss 段和.data 段): 存放全局变量和静态变量,程序运行结束操作系统自动释放,在 C 语言中,未初始化的放在.bss 段中,初始化的放在.data 段中,C++ 中不再分区了
- 常量存储区 (.data 段) : 存放的是变量,不允许修改,程序运行结束自动释放
- 代码区 (.text 段): 存放代码,不允许修改,但可以执行。编译后的二进制文件存放在这里
说明:
- 从操作系统本身来讲,以上存储区在内存中的分布是如下形式 (从低地址到高地址): .text 段–>.data 段–>.bss 段–> 堆–>unused–> 栈–>env 对于 bss 的详见 关于 text 段、data 段和 bss 段
# 实例
1 |
|
# 关于 text 段、data 段和 bss 段
# bss
Block Started by Symbol
通常是指用来存放程序中未初始化的全局变量的一块内存区域,BSS 段属于静态内存分配,用户应该将它定义在可读写的 RAM 区内, 源程序中使用malloc分配的内存就是这一块.
# text
text 段是程序代码段,它是由编译器在编译连接时自动计算的
# data
静态初始化的数据,所以有初值的全局变量和 static 变量在 data 区,他和程序大小无关,和全局变量,常量数量有关.
# stack
栈常用来存放暂时存储的信息,所以当调用函数或过程后,将会清除栈上保存的局部变量,函数调用信息及其他信息。栈是系统自动分配的,系统自动分配栈空间时,如果剩余空间大于申请空间,则自动分配成功,否则分配失败导致栈溢出。连续的一段空间,向低地址扩展,最大容量限定好的 申请效率高,程序员无法控制
# heap
堆保存函数内部动态分配的内存,更准确的说是保存程序的动态变量.
堆是程序员主动申请的 堆在内存中呈现的方式类似于链表(记录空闲地址空间的链表),在链表上寻找第一个大于申请空间的节点分配给程序,将该节点从链表中删除。大多数系统中该快空间的首地址存放的的是本次分配空间的大小,便于释放,将该块空间上的剩余空间再次连接在空闲链表上。向高地址拓展,且不连续 申请效率低,程序员可控,使用方便但是容易产生碎片
# 以上述代码来讨论栗子
本来说函数中的大部分变量都应该是局部的,但是需要注意几点
-
- 函数内部申请的空间是堆中的
-
- 函数内部的 static 变量是 Data 段的静态区
-
- 常量,如 "sac" 、 1 是放在常量区