C语言堆和栈的区别是什么?

一、问题

栈是存放函数的所有动态局部变量及函数调⽤和返回有关信息的⼀块内存。它为调试程序提供了⼀种功能,能够显示⼀个已被调⽤的函数的列表,这是调试程序时⼀种很有⽤的⼿段。

堆提供 malloc( ) , calloc( ) 和 realloc( ) 等函数获取内存空间的⼀块内存。下⾯采⽤对⽐的形式分别介绍堆和栈的作⽤,以及它们的区别。

二、解答

1. 堆和栈的作⽤

(1)栈的内存管理严格遵循先进后出的顺序,即释放栈中对象所占内存时的顺序刚好与为这些对象分配栈中内存时的顺序相反,这⼀点正是实现函数调⽤所需要的。从栈中分配内存效率特别⾼,C语⾔编译程序能产⽣如此好的代码的原因之⼀就是充分利⽤了栈。

(2)从堆中获取内存⽐从栈中获取内存要慢得多,但是堆的内存管理却⽐栈灵活得多。任何时候都可以从堆中获取内存,⽽且在释放堆中对象所占内存时,可以按任意顺序进⾏。数据对象使⽤栈中内存⽐使⽤堆中内存程序运⾏更快。但是,有时候使⽤堆中内存可以改善⼀种算法,从⽽使它更快,或者更灵活,因此使⽤堆或栈要折中考虑。

2. 堆和栈的区别

在了解了堆和栈各⾃的⽤途后,从两者的申请⽅式、申请后系统的响应、申请⼤⼩的限制、申请效率的⽐较和存储内容各⽅⾯了解它们的实质区别。

(1)申请⽅式

栈是由系统⾃动分配。如声明在函数中的⼀个局部变量 "int i;",系统会⾃动在栈中为 i 开辟内存空间。⽽堆是程序员⾃⼰申请,同时指明⼤⼩。在C语⾔中,堆提供 malloc( ) ,calloc( ) 和 realloc( ) 等函数获取内存空间的⼀块内存,如 " buffer=(int*)malloc(256) "是为 buffer 分配了⼀个256 字节⼤⼩的 int 型内存空间。

(2)申请后系统的响应

只要栈的剩余空间⼤于所申请空间,系统将为程序提供内存,否则将报异常,提示栈溢出。⽽堆则是⾸先确定操作系统有⼀个记录空闲内存地址的链表。当系统收到程序的申请时,会遍历此链表,寻找第⼀个⼤于所申请空间的堆结点, 然后将该结点从空闲结点链表中删除,并将该结点的控件分配给程序。

(3)申请⼤⼩的限制

在 windows 下,栈是向低地址扩展的数据结构,是⼀块连续的内存区域。它的最⼤容量是预先规定好的,如果申请的空间超过栈剩余的空间,将会提示溢出,能从栈获得的空间较⼩。⽽堆是向⾼地址扩展的数据结构,是不连续的内存区域。

这是因为系统是⽤链表来存储空闲内存地址的,⽽链表的遍历⽅向是由低地址向⾼地址, 堆的⼤⼩受限于计算机系统中有效的虚拟内存。因此,堆获得的空间⽐较灵活,也⽐较⼤。

(4)申请效率

在申请⽅式中,已经得知栈是由系统⾃动分配的,速度⽐较快,不容易控制。⽽堆是由 new 分配的内存,速度⽐较慢,⽤起来较⽅便。

(5)存储内容

在函数调⽤时,第⼀个进栈的是主函数中的下⼀条指令(函数调⽤语句的下⼀条可执⾏语句)的地址,然后是函数的各个参数。在⼤多数 C 编译器中,参数是由右往左⼊栈的,然后是函数中的局部变量。

注意,静态变量是不⼊栈的。当本次函数调⽤结束后,局部变量先出栈,然后是参数,最后栈顶指针指向最开始存的地址,也就是 主函数中的下⼀条指令,程序由该点继续运⾏。⽽堆⼀般是在堆的头部⽤⼀个字节存放堆的⼤⼩,堆中的具体内容由程序员安排。

三、总结

通过对栈和堆的⽐较,⼤致了解了堆和栈的区别,以及⽤途。其实,栈和堆的关系可以理解为机洗⾐服和⼿洗⾐服。全⾃动洗⾐机洗⾐服,将所有的脏⾐服放进去,倒上⽔, 放上洗⾐液就可以了。这样很便捷,但是灵活度和⾃由度较⼩。⼿洗⾐服虽然很累,但是可以将⾃⼰认为⽐较脏的局部地⽅多洗洗或分类洗,灵活度较⼤。

相关推荐
不写八个5 分钟前
Python办公自动化教程(005):Word添加段落
开发语言·python·word
HEX9CF9 分钟前
【CTF Web】Pikachu xss之href输出 Writeup(GET请求+反射型XSS+javascript:伪协议绕过)
开发语言·前端·javascript·安全·网络安全·ecmascript·xss
赵荏苒34 分钟前
Python小白之Pandas1
开发语言·python
丶Darling.36 分钟前
代码随想录 | Day26 | 二叉树:二叉搜索树中的插入操作&&删除二叉搜索树中的节点&&修剪二叉搜索树
开发语言·数据结构·c++·笔记·学习·算法
人生の三重奏43 分钟前
前端——js补充
开发语言·前端·javascript
平凡的小码农1 小时前
JAVA实现大写金额转小写金额
java·开发语言
yttandb1 小时前
重生到现代之从零开始的C语言生活》—— 内存的存储
c语言·开发语言·生活
我明天再来学Web渗透1 小时前
【hot100-java】【二叉树的层序遍历】
java·开发语言·数据库·sql·算法·排序算法
结衣结衣.2 小时前
python中的函数介绍
java·c语言·开发语言·前端·笔记·python·学习
茫茫人海一粒沙2 小时前
Python 代码编写规范
开发语言·python