我创建了一个C程序,我应该读取一个文本文件并通过int和字符串指针将它分配给一个结构。
这是我程序的代码片段:
i = 0;
while(!feof(phoneBook)) {
fscanf(phoneBook, "%d|%s\n", &num, fname);
info[i].phone_num = num;
printf("%d\n", info[i].phone_num);
info[i].first_name = fname;
printf("%s\n", info[i].first_name);
i++;
ctr++;
printf("\nfirst:%s", info[0].first_name);
printf("\nsecond:%s", info[1].first_name);
printf("\nthird:%s\n\n", info[2].first_name);
}
在第一次迭代中,它将第一行分配给info的0索引。 对于第二次迭代,它将第二行分配给索引1并替换索引0。
文本文件仅包含以下行(用于测试目的): 第一 第二 第三
这是输出:
//first iteration
first:first
second: <null>
third: <null>
//second
first:second
second: second
third: <null>
//third
first:third
second: third
third: third
顺便说一句,我宣布我的结构为:
typedef struct{
int id;
char *first_name;
char *last_name;
int phone_num;
} phone_det;
其中phoneBook是在数据类型phone_det下声明的。
任何形式的帮助将不胜感激!我刚开始使用C,我仍然可以对指针感到困惑。 :(
答案 0 :(得分:2)
虽然我们看不到你的结构,但每次将指针分配给同一名称缓冲区,并且不要将名称缓冲区本身复制到特定的数组,所以你最终有许多不同的指向同名缓冲区的指针。
答案 1 :(得分:1)
问题是作业info[i].first_name = fname;
。这不会复制字符串 - 它只是将info[i].first_name
设置为指向fname
指向的相同内存。因此,在每次迭代之后,它们都指向fname
指向的相同内存。因此,当您在缓冲区中fscanf
一个新值时,所有结构都会看到新内容。
答案 2 :(得分:1)
您指定info[i].first_name
指向fname;
而不是将fname
声明为:char* fname;
(正如我假设您所做的那样),请执行以下操作:{{ 1}}然后使用char[MAX_SIZE] fname;
复制值。所以:strcpy
答案 3 :(得分:0)
这是一个猜测,因为我看不到你的所有代码,但我敢打赌,你只需要为这些项目设置char *,就是你将指针分配给一个字符串。
fname
实际上是一个缓冲区。 (也许是一个char fname [20])所以每个项目都指向fname
,每次读取都会随之改变。
要解决此问题,请使结构包含数组。然后使用strcpy
或strncpy
从fname复制它。
答案 4 :(得分:0)
您应该复制名称,而不是指向它。您将所有指针设置为您读取姓氏的位置。使用strcpy
或其他一些。
或者,为了让生活更简单,请确保为first_name
元素分配了足够的空间,然后直接读入
fscanf(phoneBook, "%d|%s\n", &(info[i].phone_num), info[i].first_name);
答案 5 :(得分:0)
每次迭代都会读入fname
,然后将fname
的地址分配给info[i].first_name
。 fname
的地址在每次迭代之间不会改变,因此您要为所有first_name
指针分配相同的地址!
您需要为每次迭代分配一个唯一的数组,以便将字符串存储在不同的位置,而不是每个都覆盖最后一个。
while(!feof(phoneBook)) {
char *fname = malloc(SUITABLY_LARGE_SIZE);
if (fname == NULL) {
perror("malloc");
exit(1);
}
fscanf(phoneBook, "%d|%s\n", &num, fname);
info[i].first_name = fname;
...
}