C语言合并Q1/Q2/Q3.txt生成FINAL起跑名单输出行数不符问题求解
问题产生原因
- 输出文件重复打开且使用覆盖模式:
fopen("./data/FINAL", "w")被写在了遍历三个输入文件的for循环内部,w模式的特性是打开文件时直接清空原有内容,所以每处理完一个输入文件,之前写入FINAL的内容都会被清空,最终文件里只剩下最后处理的Q1.txt写入的内容,这是行数远少于预期的核心原因。 - 行号判断逻辑错误:
- 计数变量j从0开始,循环内先执行
j++再判断,Q3取前10行的判断条件j >= 0 && j < 10实际只会取到j=1到j=9共9行,漏了第10行; - Q2需要取10~15行共6行,现有判断
j >=10 && j <15只会取到j=10到j=14共5行,漏了第15行; - Q1需要取15~20行共6行,现有判断
j >=15 && j <20只会取到j=15到j=19共5行,漏了第20行。
- 计数变量j从0开始,循环内先执行
- 输出文件名不符合要求:需求是生成
FINAL.txt,代码里输出文件名写的是FINAL,缺少.txt后缀。 - 多余换行符:
fgets读取的行内容本身自带末尾的换行符,fprintf额外加\n会导致每行之间多一个空行。
修复方案
调整输出文件的打开位置到for循环外部,全程只打开一次写入;修正行号判断逻辑;修正输出文件名;去掉多余的换行符,修复后的代码如下:
void prepaClassementFinal(void) { #define NUMBER_OF_STRING 3 #define MAX_STRING_SIZE 14 char arr[NUMBER_OF_STRING][MAX_STRING_SIZE] = {"./data/Q3.txt", "./data/Q2.txt", "./data/Q1.txt"}; // 输出文件移到循环外打开,仅初始化一次 FILE *fichier = fopen("./data/FINAL.txt", "w"); if (fichier == NULL) { perror("fopen() failed !"); exit(EXIT_FAILURE); } for (int i = 0; i < NUMBER_OF_STRING; i++) { FILE* file = fopen(arr[i], "r"); if (file == NULL) { perror("fopen input file failed !"); fclose(fichier); exit(EXIT_FAILURE); } char line[256]; int j = 0; while (fgets(line, sizeof(line), file)) { j++; if(i == 0) { // 取Q3前10行 if(j <= 10) { fprintf(fichier, "%s", line); } } if(i == 1){ // 取Q2第10~15行 if(j >= 10 && j <= 15) { fprintf(fichier, "%s", line); } } if(i == 2){ // 取Q1第15~20行 if(j >= 15 && j <= 20) { fprintf(fichier, "%s", line); } } } fclose(file); } // 所有内容写完再关闭输出文件 fclose(fichier); }
内容的提问来源于stack exchange,提问作者bendour
相关产品推荐
相关产品推荐

