Nic*_*ico 1 c arrays struct loops
我正在学习C,我正在玩结构,但我发现了一些我无法解释的行为,我想知道它为什么会发生.
这是我的代码:
struct my_struct{
char *name;
};
int main()
{
struct my_struct arr[3];
int i = 0;
char str[10];
while (i<3)
{
fgets(str, 10, stdin);
arr[i].name = str;
printf("Array number %d: %s", i, arr[i].name);
i++;
}
printf("1 - %s\n2 - %s\n3 - %s", arr[0].name, arr[1].name, arr[2].name);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
我的意见:
test1
test2
test3
Run Code Online (Sandbox Code Playgroud)
预期产量:
Array number 0: test1
Array number 1: test2
Array number 2: test3
1 - test1
2 - test2
3 - test3
Run Code Online (Sandbox Code Playgroud)
结果输出:
Array number 0: test1
Array number 1: test2
Array number 2: test3
1 - test3
2 - test3
3 - test3
Run Code Online (Sandbox Code Playgroud)
结果输出:
问题是,只要while循环继续运行,它似乎没问题; 但是,当它退出时,它似乎将数组中结构的每个"名称"值设置为最后一个.
如果,一旦离开循环并在最后一个printf()之前,我手动设置数组中最后一个结构的名称,这是唯一一个更新的结构,但前面的结构名称仍然设置为最后一个进入循环内部.
我想我错过了关于内存管理的事情,比如在再次调用fgets()之前刷新缓冲区,或者无法弄清楚发生了什么.有谁知道这是关于什么的?
这就是你所期望的,你可以这样思考char str[10],这是你的字符串存储的内存.当您设置每个数组名称时,arr[i].name = str您指向char * name此内存.所以这是你的for循环正在做的事情:
0. str = []; arr[0].name = NULL; arr[1].name = NULL; arr[1].name = NULL;
1. str = [string1]; arr[0].name = str; arr[1].name = NULL; arr[1].name = NULL;
2. str = [string2]; arr[0].name = str; arr[1].name = str; arr[1].name = NULL;
3. str = [string3]; arr[0].name = str; arr[1].name = str; arr[1].name = str;
Run Code Online (Sandbox Code Playgroud)
因此,在循环结束时,所有arr.name指针都指向字符串,并且每次都编辑了字符串.如果您希望单个arr元素存储自己的字符串,那么最好这样做:
struct my_struct{
char name[10]; // Note how each instance of `my_struct` now stores its own string.
};
int main() {
struct my_struct arr[3];
int i = 0;
while (i<3) {
fgets(arr[i].name, 10, stdin);
printf("Array number %d: %s", i, arr[i].name);
i++;
}
printf("1 - %s\n2 - %s\n3 - %s", arr[0].name, arr[1].name, arr[2].name);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
作为最后一点,你应该避免使用fgets (见这里).更喜欢getline.