You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C语言用fgets读取文本文件:非\0与\n的神秘字符排查及解决

fgets读取文本后strcmp不匹配的原因与解决办法

问题场景

我查遍了相关内容,还是遇到了这个问题:

我的C代码里定义了常量ESCAPE = "1a2b3c4e5d",用fgets读取backup.txt的内容,文件第一行是1a2b3c4e5d\r\n(Windows格式换行)。尝试去除换行符后和ESCAPE做strcmp,始终匹配失败。

相关代码片段:

const char *ESCAPE= "1a2b3c4e5d";
FILE *FP= fopen("backup.txt", "r");

char line[64];
while(fgets(line, sizeof(line), FP)){
   fprintf(stdout, "this is line lenght: %ld", strlen(line));
   // 输出结果为12
   line[strlen(line) -1]= 0; // 尝试去除换行符
   fprintf(stdout, "This is line after getting rid of new_line: %ld\n", strlen(line));
   // 输出结果为11
   fprintf(stdout, "This is ESCAPE lenght: %ld\n", strlen(ESCAPE));
   // 输出结果为10

   if(strcmp(line, ESCAPE) == 0){
      fprintf(stdout, "I'm Here\n");
   }
}

按预期,第一行10个有效字符加\n应该是11长度,去除后应该是10,但实际去除后长度是11,导致strcmp无法匹配。

原因分析

这个"神秘字符"是回车符\r。Windows系统的文本文件换行采用\r\n(回车+换行)组合,fgets会把这两个字符都读入缓冲区。原代码只去掉了最后一个\n,但\r仍留在字符串中,导致长度多1,strcmp自然无法匹配。

解决方案

使用strcspn函数一次性处理\r和\n,替换原有的去除换行代码:

line[strcspn(line, "\r\n")] = '\0';

strcspn会返回字符串中第一个属于"\r\n"集合的字符的位置,直接将该位置设为字符串终止符,不管是单个\n、单个\r还是\r\n组合,都能一次性清理干净。

补充说明

部分操作系统课程可能未提及\r字符的存在,这个方案对遇到相同跨平台文本换行问题的开发者会很有用。


内容的提问来源于stack exchange,提问作者ZODIACK

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 23:15:54