从文本文件中移除指定字符串数组内单词的C语言代码故障排查求助
解决文件单词过滤代码的问题
我来帮你看看这段代码的问题所在,你想要实现的是从每行一个单词的文件里过滤掉指定单词,输出剩下的到新文件,但代码里有几个关键逻辑和写法问题导致不符合预期:
原代码的核心问题
while(!feof(inp))的错误用法:这个判断会导致最后一行被重复处理,因为feof只有在读取操作尝试读取到文件末尾之后才会置位。当最后一次fgets成功读取后,循环还会再执行一次,此时fgets会失败,但word里保留的是上一次的内容,导致错误处理。- 循环逻辑混乱:你在
while循环里嵌套了for循环,每次for循环迭代都调用fgets,这意味着一次while循环会读取13个单词(除非中途强制跳出),完全不符合“逐行读取并检查”的逻辑。而且在else分支里设置i=14跳出for循环的写法不仅不规范,还会打乱循环的正常流程。 - 字符串数组空间不足:你定义
toremove[][5],但像"that\n"这样的字符串,加上结束符'\0'需要6个字节的空间(t、h、a、t、\n、\0),数组的5字节空间会导致字符串被截断,没有正确的终止符,strcmp无法正确匹配这些字符串,自然匹配不到你想移除的单词。 - 没有写入输出文件:代码里只有
printf调试输出,完全没有把符合条件的单词写入到outp指向的out2.dat.txt文件里。
修正后的代码
#include <stdio.h> #include <stdbool.h> #include <string.h> #include <stdlib.h> int main(void) { FILE *inp; FILE *outp; char word[16]; // 用指针数组存储要移除的单词,避免空间不足问题 const char *toremove[] = {"is\n", "a\n", "and\n", "with\n", "By\n", "that\n", "to\n", "It\n", "has\n", "in\n", "for\n", "from\n"}; // 计算要移除的单词数量,避免硬编码数字 int remove_count = sizeof(toremove) / sizeof(toremove[0]); // 打开文件时检查是否成功,避免后续操作崩溃 inp = fopen("out1.dat.txt", "r"); if (inp == NULL) { perror("Failed to open input file"); return EXIT_FAILURE; } outp = fopen("out2.dat.txt", "w"); if (outp == NULL) { perror("Failed to open output file"); fclose(inp); // 已打开的输入文件要及时关闭 return EXIT_FAILURE; } // 正确的逐行读取循环:fgets成功读取内容时进入循环 while (fgets(word, sizeof(word), inp) != NULL) { bool should_remove = false; // 遍历过滤词列表,检查当前行是否需要移除 for (int i = 0; i < remove_count; i++) { if (strcmp(word, toremove[i]) == 0) { should_remove = true; break; // 找到匹配就跳出循环,不用继续检查 } } // 如果不需要移除,就写入输出文件 if (!should_remove) { fputs(word, outp); printf("保留单词:%s", word); // 调试用输出,可按需删除 } else { printf("移除单词:%s", word); // 调试用输出,可按需删除 } } // 关闭所有打开的文件 fclose(inp); fclose(outp); return EXIT_SUCCESS; }
关键改动说明
- 替换错误的循环条件:用
fgets的返回值作为循环条件,确保只有成功读取到一行内容时才处理,避免末尾重复或错误。 - 改用指针数组存储过滤词:
const char *toremove[]可以正确存储任意长度的字符串(只要不超过word的长度),解决了原数组空间不足导致的字符串截断问题。 - 重构检查逻辑:逐行读取后,遍历过滤词列表判断是否需要移除,逻辑清晰,不会出现原代码中一次读取多个单词的问题。
- 增加文件打开错误检查:避免文件打开失败时程序继续执行导致的崩溃。
- 实现输出文件写入:用
fputs把不需要移除的单词写入到out2.dat.txt,完成你原本的需求。
内容的提问来源于stack exchange,提问作者Tom Snow
相关产品推荐
相关产品推荐

