C-堆栈变量在迭代之间消失

时间:2015-10-07 02:31:29

标签: c pointers stack

嗨,我是C的新手并且花了太长时间试图找到这个bug。以下是发生的事情的一个例子:

#include <stdio.h>


struct Garbage {
  int value;
};

int main(int argc, char *argv[]) {
  int i = 0;
  struct Garbage* pointers[10];
  while (i < 10) {
    struct Garbage temp = { .value = i * 7 };
    pointers[i] = &temp;
    i++;
  }

  for (int i = 0; i < 10; i++) {
    printf("pointers[%d]->value %d\n", i, pointers[i]->value);
  }
}

为什么打印

pointers[:]->value: [63, 63, 63, 63, 63, 63, 63, 63, 63, 63, ]

我认为这是因为在while循环的每次迭代中,temp都被放置在堆栈的相同位置。但为什么会这样呢?为什么C认为它可以破坏我的变量? 这里有什么名字?我试图找到相关信息,但无法做到。所以,如果你告诉我这叫做什么,我将能够自己做一些搜索。非常感谢!

1 个答案:

答案 0 :(得分:3)

您未正确分配temp

struct Garbage* pointers[10];
while (i < 10) {
    struct Garbage temp = { .value = i * 7 };
    pointers[i] = &temp;
    i++;
}

一旦struct Garbage temp超出范围(或者每次迭代结束时),您就不再拥有指针所指向的任何内存。访问该内存是不确定的行为。

可能发生的是为每个创建的struct Garbage temp分配相同的堆栈空间,因此所有指针可能都指向相同的内存地址。您可以使用printf("%p\n", pointers[i])验证(所有指针都是相同的)。

解决此问题的一种方法是使用malloc

struct Garbage* pointers[10];
while (i < 10) {
    pointers[i] = malloc(sizeof(struct Garbage));
    pointers[i]->value = i * 7;
    i++;
}

在完成这些指示后,请记住free所有指针。