C语言替换TXT读取方案:dup改为fgets+sscanf校验每行2个数字
实现方案
原有代码的错误点
- 第一段代码中
dup2的判断逻辑括号位置错误,未定义numOfPairs、numbersInPair、arrNum变量,也没有行号校验逻辑,scanf无法识别单行内的数字个数 - 第二段代码提前用
getc遍历完了整个文件,后续fscanf读取位置已经是文件末尾,arrIndex + 2是无效表达式没有完成赋值操作,同样没有行校验逻辑
正确实现代码
#include <stdio.h> #include <stdlib.h> #include <string.h> int main() { FILE* fp = fopen("./pairs.txt", "r"); if (fp == NULL) { perror("文件打开失败"); return 1; } char buf[256]; int line_num = 0; int num_of_pairs = 0; int* arr_num = NULL; int arr_idx = 0; // 读取第一行声明的总对数 if (fgets(buf, sizeof(buf), fp) != NULL) { line_num++; if (sscanf(buf, "%d", &num_of_pairs) != 1 || num_of_pairs <= 0) { printf("illegal input at line %d\n", line_num); fclose(fp); return 1; } arr_num = (int*)malloc(sizeof(int) * num_of_pairs * 2); if (arr_num == NULL) { printf("内存申请失败\n"); fclose(fp); return 1; } } else { printf("文件为空\n"); fclose(fp); return 1; } // 逐行读取数字对 while (fgets(buf, sizeof(buf), fp) != NULL) { line_num++; // 跳过空行 if (buf[0] == '\n' || buf[0] == '\r') continue; int a, b, extra; // 尝试读取3个整数,返回值为2说明当前行刚好只有2个合法数字 int match_cnt = sscanf(buf, "%d %d %d", &a, &b, &extra); if (match_cnt != 2) { printf("illegal input at line %d\n", line_num); free(arr_num); fclose(fp); return 1; } arr_num[arr_idx++] = a; arr_num[arr_idx++] = b; // 超过声明的对数判定为非法 if (arr_idx / 2 > num_of_pairs) { printf("illegal input at line %d: extra pairs beyond declared count\n", line_num); free(arr_num); fclose(fp); return 1; } } // 校验实际读取的对数和声明是否一致 if (arr_idx / 2 != num_of_pairs) { printf("illegal input: actual pair count %d not equal to declared %d\n", arr_idx/2, num_of_pairs); free(arr_num); fclose(fp); return 1; } // 正常业务逻辑可在此处添加,示例输出读取结果 printf("读取成功,共%d对数字:\n", num_of_pairs); for (int i = 0; i < arr_idx; i += 2) { printf("%d %d\n", arr_num[i], arr_num[i+1]); } free(arr_num); fclose(fp); return 0; }
核心逻辑说明
- 用
fgets逐行读取内容到缓冲区,避免跨行读取的问题 - 用
sscanf尝试读取3个整数,返回值为2说明当前行刚好只有2个合法数字,返回值大于2说明行内有多余数字,小于2说明数字个数不足 - 全程计数行号,遇到非法情况直接输出对应行号并退出
- 额外增加了总对数校验逻辑,避免实际行数和第一行声明的数量不匹配的问题
内容的提问来源于stack exchange,提问作者linorkhbur
相关产品推荐
相关产品推荐

