为啥 malloc() 和普通数组声明分配的堆栈帧大小不同?

Posted

技术标签:

【中文标题】为啥 malloc() 和普通数组声明分配的堆栈帧大小不同?【英文标题】:Why is the assigned stack frame size is different for malloc() and normal array declaration?为什么 malloc() 和普通数组声明分配的堆栈帧大小不同? 【发布时间】:2020-01-28 21:44:25 【问题描述】:

我有两个非常简单的递归 C 程序。我正在检查系统分配给每个递归帧的堆栈帧大小。但是我遇到了一些我不明白的事情。

当我在递归函数中创建一个大小为 5 的本地数组时,系统会为每一帧分配 48 个字节。

当我创建一个指针并用size*sizeof() 分配相同数量的内存时,系统会为每一帧分配32 个字节。

我检查的方式是,我将我的 C 代码编译成程序集并查看分配的字节。我对差异的猜测是malloc 从堆中分配,而普通数组声明从堆栈中分配。所以我在想这两个内存部分可能有不同的程序?

我期望分配的内存是相同的,但它们是不同的。

我从主函数调用它们。

void RecursiveFunction( int n )

    int *point;
    point = (int *)malloc(sizeof(int)*5);

    if ( n > 1)
        RecursiveFunction( --n );
    return;

#include <stdio.h>
#include <stdlib.h>

void RecursiveFunction( int n )

    int arr[5];

    if ( recursion_times > 1)
        RecursiveFunction( --n );

    return;

【问题讨论】:

c++: local array definition versus a malloc call的可能重复 假设“零”帧大小为 28 字节,在第一种情况下,您有 28 + sizeof(int*),在您的系统上是 32,在第二种情况下是 28 + sizeof(int) * 5,即 48。 但是我们用 (int *)malloc(sizeof(int)*5) 分配了额外的内存。不占空间吗? sizeof(int)*5 字节是从堆中分配的。在堆栈上只有一个指向它的指针 (int*)。 非常感谢,这解决了我的问题 【参考方案1】:

只是为了完整性:

mallocheap 分配空间,而局部变量在 stack 上分配。假设 int 是 4 个字节,则您的数组占用 4*5=20 个字节。当您使用malloc 分配数组时,实际的数组不是堆栈帧的一部分,而是您恢复malloc 返回的地址的指针,这就解释了为什么在堆栈帧大小为 20-4=16。

【讨论】:

以上是关于为啥 malloc() 和普通数组声明分配的堆栈帧大小不同?的主要内容,如果未能解决你的问题,请参考以下文章

结构中的数组和结构的 Malloc

何时在声明或初始化时为变量分配内存?

C 数组 malloc() VS

malloc 和全局变量声明在 C 中将它们的变量分配到哪里? [复制]

当我们有一个红色区域时,为啥我们需要堆栈分配?

计算机内存为啥要有堆栈区?