我应该创建一个包含以下属性的链表:
struct node{
char *word;
int times;
struct node *next;
}head;
我必须从文件中读取每个单词,检查它是否存在于列表中,如果它不存在,我应该添加它。如果它已经存在,我需要将times
增加一个。我使用以下代码来实现:
void append(char *wrd, struct node *start){
struct node *current = start;
while(current->next != NULL){
current = current->next;
}
current->next = malloc(sizeof(struct node));
strcpy(current->word, wrd);
current->times = 1;
current->next->next = NULL;
}
int iterate(char *wrd, struct node *start){
struct node *current = start;
while(current != NULL){
if(strcmp(current->word, wrd)==0){
current->times++;
return 1;
}
current = current->next;
}
return 0;
}
void read_file(struct node *start){
FILE *fp;
char wrd[20];
puts("give file name and format(max 19 characters)");
gets(wrd);
fp = fopen((const char*)wrd, "r");
fscanf(fp, "%s", wrd);
start->word = malloc(strlen(wrd)+1);
strcpy(start->word, wrd);
while(fscanf(fp, "%s", wrd) != EOF){
if(!iterate(wrd, start)){
append(wrd, start);
}
}
}
void print_data(struct node *start){
struct node *current = start;
while(current->next != NULL){
printf("word: %s , times: %d", current->word, current->times);
}
}
int main(int argc, char *argv[]) {
struct node *start = &head;
read_file(start);
return 0;
}
append
接受一个字,创建一个包含它的新节点,并将该节点添加到列表中。
iterate
接受一个单词并在列表中搜索匹配项。如果列表中已存在该单词,则times
将增加1。如果未找到匹配项,则会返回0
,而在相反的情况下会返回1
。
read_file
初始化头节点,读取文件并为其读取的每个单词调用上述函数。
假设我有一个包含以下字词的文本文件:
hello hey world hello
world this is supposed to work
but it does not
程序成功运行前3个单词并创建节点。找到匹配hello
后,程序崩溃。我已经确定错误在于iterate
,但我无法弄清楚导致它的原因。非常感谢任何帮助。
答案 0 :(得分:0)
首先,我不明白为什么你可以自信地说你的程序在iterate
函数中有错误。
在word
之前,您尚未向strcpy()
指针分配任何内存。
我建议你在append()
函数中执行此操作:
void append(char *wrd, struct node *start){
struct node *current = start;
if(current == NULL){
start = (struct node*)malloc(sizeof(struct node));
start->word = (char *)malloc((strlen(wrd) + 1)*sizeof(char));
strcpy(start->word, wrd);
start->times = 1;
start->next = NULL;
return;
}
while(current->next != NULL){
current = current->next;
}
current->next = (struct node*)malloc(sizeof(struct node));
current->next->word = (char*)malloc((strlen(wrd) + 1)*sizeof(char)); //add this line
strcpy(current->next->word, wrd); //not current->word
current->next->times = 1; //not current->times
current->next->next = NULL;
}
请注意,在append函数中,您没有检查列表是否已经为空。 if
块也是这样做的。还要注意使用strcpy()
时犯的错误。您希望在新指针中复制新单词,但是在指针中执行它,该指针是新节点的父指针。
现在,您read_file()
功能看起来会简单得多!
void read_file(struct node *start){
FILE *fp;
char wrd[20];
puts("give file name and format(max 19 characters)");
gets(wrd);
fp = fopen((const char*)wrd, "r");
while(fscanf(fp, "%s", wrd) != EOF){
if(!iterate(wrd, start)){
append(wrd, start);
}
}
}
我认为您的iterate
功能不需要更新,但print_data()
肯定会:
void print_data(struct node *start){
struct node *current = start;
while(current != NULL){
printf("word: %s , times: %d", current->word, current->times);
current = current->next;
}
}
似乎唯一没有任何错误的函数是iterate()
。当你玩指针时会发生! :P