基础——堆和栈的区别

堆和栈的区别在许多的面试中都有提及,他们的区别在计算机编程中也是属于非常基础的部分,不过我之前一直没去了解……

不过在了解之后也很简单的。

首先我们要知道程序所占的内存一共分为5大块,分别是

1、堆

2、栈

3、初始化区

4、未初始化区

5、代码区


堆——由程序员分配内存释放的,比如new指令、alloc指令和malloc指令

栈——由编译器自己分配释放的,用来存放一些参数值,局部变量的值之类的,就是除了堆和static和const以外的就都是栈了,一般编译器的栈大小是已经固定好的


借鉴一个程序代码的例子:

 

这是一个前辈写的,非常详细    
  //main.cpp    
  int   a   =   0;   全局初始化区    
  char   *p1;   全局未初始化区    
  main()    
  {    
  int   b;   栈    
  char   s[]   =   "abc";   栈    
  char   *p2;   栈    
  char   *p3   =   "123456";   123456/0在常量区,p3在栈上。    
  static   int   c   =0;   全局(静态)初始化区    
  p1   =   (char   *)malloc(10);    
  p2   =   (char   *)malloc(20);    
  分配得来得10和20字节的区域就在堆区。    
  strcpy(p1,   "123456");   123456/0放在常量区,编译器可能会将它与p3所指向的"123456"  
  优化成一个地方。    
  }    
a在初始化区

p1在未初始化区

b这里虽然没给他值,但是他还是占有一个随机值,字节为4,放在了栈中

s数组为字符数组,已初始化,大小为4,放在栈中

p2指针,32位计中固定占了4字节,栈中

p3指针,4字节,栈中,指向常量区中的123456/0的首字节

c 初始化区

之后是为p1、p2开辟了10和20字节的堆区域

strcpy是为p1赋值,如果进行了优化,就指向了常量区,否则就把值放入堆中


堆和栈的比较:

1、开辟方式

栈是在你定义之后直接由模拟器给你开辟的空间

例如p2,p3

堆是由程序员申请的大小,如malloc(10)就是申请10字节大小的空间

直接用new的话就是申请对象所占的字节空间


2、大小

栈是固定的常量,由模拟器决定

堆的大小为计算机系统中有效的虚拟内存容量。所以堆的容量远远的大于栈


3、存储方式

栈由于是编译器申请的,所以它所开辟的空间都是连续行的,即使在释放之后也不会产生什么碎片。

堆得位置都是随机生成的,所以他比较自由,例如链表你是没法通过简单的加上所占字节得到下一个链的位置,同时由于随机,堆会产生碎片,不过用起来比较方便


4、响应

栈的响应速度快,不过栈所申请的内存必须小于剩余空间,否则会报栈溢出

堆得响应速度偏慢,它在申请的时候会在一个空闲表找到一个堆节点大于所申请的空间,并且把这个节点分配给堆,多于的大小重新放入空闲表中

(PS:操作系统有一个记录空闲内存地址的链表)(PPS: 所谓的碎片就是空闲表中太小的空间,在两块已经被申请的空间中间并且基本上不会被用到的)


5、效率

效率嘛,不用多想,肯定是栈快


总结

堆和栈各有好坏

栈快但又不灵活而且还小

堆慢但是灵活,可分配内存大

在使用上栈比堆简单,所以若是占内存小且不是特别的扣内存的话,不妨用栈的简单


   

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值