【函数栈帧与销毁(初步解读)】

你好,这里是新人 Sunfor

这篇是我最近对于函数栈帧与销毁的学习心得
有任何错误欢迎指正,欢迎交流!
会持续更新,希望对你有所帮助,我们一起学习,一起进步

前言

提到函数的栈帧与销毁,大家可能会觉得很陌生同时难以理解
但是理解了函数的栈帧与销毁之后,我们对后面数据结构的理解函数运用代码运行结果可能又会多增加一个视角
那么接下来我们一起学习~

一、何为栈

1.栈在计算机中的位置

计算机的内存结构通常分为几个区域:代码段、数据段、堆和栈
在这里插入图片描述

2.栈的概念

  • 栈 是一种数据结构,遵循“后进先出” or “先进后出”的原则。在栈中最后被插入的元素最先被移除
  • 栈一般向下生长,即高地址向低地址分配内存。这与堆的生长方向相反
  • 栈的大小是有限的,通常由操作系统配置。之前我们提到的过大的函数递归操作可能会导致栈溢出,这会导致程序崩溃
  • 栈的访问速度非常快,因为它采用的是连续的内存空间,并且其操作主要通过指针实现
    在这里插入图片描述

3.栈的基本操作

  • 压栈(Push):将一个元素添加到栈顶
  • 弹栈(Pop):移除并返回栈顶的元素
  • 查看栈顶(Peek/Top):查看栈顶元素但不能移除它
  • 判断空栈(IsEmpty):检查栈是否为空

4.栈的应用

  • 函数调用管理:在程序执行过程中,用于保存函数调用的上下文信息
  • 表达式求值:用于实现后最表达式和中缀表达式转换
  • 回溯算法:深度优先搜索,需要记录路径或状态

二、何为函数的栈帧与销毁

  • 函数的栈帧
    栈帧是 在函数调用的同时在栈上分配的一块内存区域,用于存储该函数的运行所需信息
    每次函数被调用时,都会创建一个新的栈帧
  • 栈帧的销毁
    函数执行完毕后,其对应的的栈帧会销毁,释放其占用的空间。这是由程序运行时的栈管理机制自动处理的

三、寄存器

1.寄存器的概念

寄存器是计算机内部放入一种高速存储器,用于临时存储数据和指令。它们位于中央处理器(CPU)内部,能够快速存取,通常用于存放当前正在处理的数据、指令地址以及其他重要信息

2.寄存器的作用

  • 快速存取:寄存器是CPU内部的告诉存储器,访问速度远快于内存,因此在计算时优先使用寄存器
    -参数传递:在许多调用约定中,函数的参数通常通过寄存器传递,而不是堆栈,这样可以加快函数调用的效率
  • 返回值:函数的返回值通常也可以通过特定的寄存器传递给调用者
  • 临时存储:寄存器可以用于存放在函数执行过程中需要频繁访问的临时变量

3.栈帧和寄存器的协作

当一个函数被调用时,当前的寄存器状态会被保存到栈帧中,以确保函数执行结束后能够恢复原来的状态
函数执行完毕后,栈帧被销毁,相关的寄存器内容更具需要恢复,确保程序能继续正确执行
在这里插入图片描述

四、函数栈帧的创建和销毁的实现过程

我们先给一个简单的代码

#include<stdio.h>
int Add(int a, int b)
{
	return a + b;
}

int main()
{
	int x, y;
	scanf("%d %d", &x, &y);

	int ret = Add(x, y);

	printf("%d", ret);
}      

首先,每一个函数调用都要在栈区创建一个空间
在这里插入图片描述
在调用函数之前先创建一块空间
在这里插入图片描述
主函数正式栈帧
注意这里如果没给形参赋值,栈里放着默认值,打印出来就是乱码
在这里插入图片描述
函数传参过程,还未调用就将寄存器压栈进入了栈内了
在这里插入图片描述
调用之前就把call指针的下一个地址保存下来了
调用时再利用指针的偏移量重新找
用完之后再 pop回原来的地址
所以,在这段简单的程序中
我们更能够理解:形参是实参的临时拷贝

当然,我们现在理解还是有些抽象,且函数栈帧的实现过程在不同的编译器上显示也有所区别,但是原理不变,学习函数栈帧与销毁是内化我们对原理的理解,现在只是基于现有知识的解读,之后有新的发现也会继续更新,大家可以持续关注!

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值