在每次调用时使用新内存地址创建变量的函数

时间:2015-12-20 13:00:31

标签: c

假设有一个函数f,它在其体内包含一个新变量b的声明。 我注意到,每次调用f时,变量b - 应该每次创建和销毁(编辑:不在动态情况下,如another (now solved) related question所指出的) - 始终具有相同的内存地址。 / p>

以下非常简单的代码显示了一个示例:

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

void f ( void ){
   int b;
   printf ("%p\n", &b);
}

int main (){
    int i = 0;
    while (++i <= 10)
        f();
return 0;
}

输出:(始终使用相同的内存地址)。

  

是否有可能以这样的方式修改f:在每次调用时,它始终使用新的内存地址创建b,与之前的每次调用不同?

编辑:一些用户建议使用内存的动态分配,但不幸的是我仍然无法解决问题。

你可以忽略这个前提,直接看我对这个问题的新表述。

让我们考虑以下代码。

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

void f ( void ){
   int * b = malloc ( sizeof(int) );
   printf ("%p\n", &b);
}

int main (){
   int i = 0;

   while (++i <= 10)
      f();
return 0;
}
  

为什么它总是产生相同的输出?

您可能很容易想象,我对C的体验有限。我们非常欢迎每一条了解更多的建议和/或参考资料。

由于

Pss:在创建一些动态结构数据(如列表或树)之前,我需要先解决这个问题。我们的想法是,每次添加节点时,新节点必须引用新的内存地址以避免循环。在我的书中写道,解决方案是使用malloc指令,我试图完全理解为什么。

2 个答案:

答案 0 :(得分:1)

自动变量的地址取决于函数入口上的堆栈指针的值,并且将是一个固定的偏移量。如果你在这样的循环中调用一个函数:

while (...) {
    ...
    f(...);
    ...
}

编译器很可能以f自动变量始终具有相同地址的方式生成代码。这是你不能轻易改变的。

如果我们不使用自动变量,我们可以轻松获得所需的结果。每次只需在f中分配一个新变量。当然,这会泄漏大量内存,但没有更好的方法,因为f必须记住已经用于b的地址,如果你想要b每次驻留在不同的地址,以前使用的地址为此目的无法使用(因而浪费)。

答案 1 :(得分:1)

也许您要找的是动态内存分配?您可能需要阅读malloccallocreallocfree的文档(<stdlib.h>中的原型。)

从技术上讲,有一个与每个对象关联的存储类。对于像f这样的自动变量,这是自动并且通常在堆栈上分配(但也有无堆栈的机器)。对于动态分配的对象,存储类是 dynamic ,它通常是从堆中分配的(但也有无堆机器)。

实质上,您不应该依赖具有特定模式或价值的地址。