【问题标题】:Free memory from stack in C从C中的堆栈中释放内存
【发布时间】:2018-11-29 01:53:49
【问题描述】:

只是想知道是否有办法在运行时释放或减少从堆栈分配的内存。 例如:

int num[10] = {1,2,3,4};

我可以在运行时释放 6*4 字节(假设 int 需要 4 个字节)吗?

【问题讨论】:

标签: c arrays memory-management stack


【解决方案1】:

局部变量使用的内存在定义它们的块结束时被回收。它们不能像动态分配的内存那样被释放。

如果您需要调整正在使用的内存量,请使用malloc / free 分配内存:

int *num = malloc(NUM_BYTES);
...
int *tmp = realloc(num, NEW_NUM_BYTES);
if (tmp) num = tmp;
...
free(num);

【讨论】:

  • 是的,我明白这一点。我的问题是 - 我可以减少运行时从堆栈中获得的内存量吗?在这种情况下是 24 字节的内存。
  • @SaurabhSuman 不,你不能。如果你想改变正在使用的内存量,你应该改用malloc / free
  • @SaurabhSuman:您要求 10 个整数,其中 4 个是非零值,6 个是零。编译器无法完成您要求它使用更少的工作。如果你写了int num[] = { 1, 2, 3, 4, };,那么你会节省空间。由于初始化程序在编译时是固定的,因此选择取决于您 — C 让您思考。
  • 具有自动存储持续时间的对象的生命周期在其块执行结束时结束,而不是在超出范围时结束。寿命是时间的持续时间。范围是代码中的位置。当一个函数调用另一个函数时,它的标识符不在被调用函数的代码范围内,但它的对象继续存在。 (另外,在函数调用期间,调用函数的执行被暂停,而不是结束。)
  • @EricPostpischil 有很好的区别。已更新以反映。
【解决方案2】:

我可以在运行时释放 6*4 字节(假设 int 需要 4 个字节)吗?

没有。自动(或静态)存储持续时间的对象在其生命周期内具有固定大小,由其声明确定。如果你想使用更少的空间,那么声明一个更小的对象。

如果您专门声明一个小型数组,直到运行时才知道它需要多大的大小,并且您只想声明实际需要的数量,那么您可以选择使用变长数组。 VLA 支持在 C2011 中是可选的,并且 VLA 带有一些固定长度数组没有的潜在问题,但如果您可以接受,那么您可以这样做:

void count_to(unsigned char max) {
    int numbers[max];
    for (int i = 0; i < max; i++) {
        numbers[i] = i + 1;
    }

    // ...
}

请注意,VLA 可能没有初始值设定项,如果最终 VLA 比您考虑的要大,您可能会遇到麻烦(例如溢出堆栈)。

您的主要选择是动态分配。动态分配数组会产生代码和性能开销,并且需要确保释放分配的内存,但所有符合要求的实现都支持它,而且它通常支持比 VLA 大得多的对象。

【讨论】:

    猜你喜欢
    • 2012-09-17
    • 2016-07-25
    • 1970-01-01
    • 1970-01-01
    • 2015-08-13
    • 1970-01-01
    • 1970-01-01
    • 2011-07-25
    • 1970-01-01
    相关资源
    最近更新 更多