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

C语言使用fscanf读取文件含空格姓名出现读取错位如何解决

C语言读取带空格姓名的文件修改方案

问题根源

fscanf的%s格式符默认以所有空白字符(空格、换行、制表符)作为分隔符,你存储姓名的行包含空格,会被拆分为两个独立字符串,导致后续字段读取错位,同时缺少姓名转小写的逻辑,无法满足输出要求。

核心修改点

针对case1的文件读取逻辑做如下调整:

  1. 读完第一行的ID后,先吃掉行尾残留的换行符,避免后续读取到空内容
  2. 用逐行读取逻辑读取姓名,自动保留姓名中间的空格
  3. 读取姓名后移除末尾自带的换行符
  4. 增加姓名转小写的逻辑
  5. 补充文件打开合法性判断、文件关闭操作,避免运行错误

修改后的完整代码

#include <stdio.h>
#include <string.h>
#include <ctype.h>
#define STRING_LENGTH 100
// 定义学生信息结构体,别名student_t
typedef struct student_t{
    char studentId[STRING_LENGTH];
    char studentName[STRING_LENGTH];
    char studentAge[STRING_LENGTH];
}student_t;

// 打印学生信息函数
void print_student(struct student_t student){
    printf("\nStudent id: %s\n", student.studentId);
    printf("full name: %s\n", student.studentName);
    printf("age: %s\n", student.studentAge);
}

// 字符串转小写工具函数
void str_to_lower(char* str) {
    for(int i = 0; str[i]; i++){
        str[i] = tolower(str[i]);
    }
}

int main() {
    struct student_t student;
    memset(&student, 0, sizeof(student));

    int option;
    printf("Choose an option: ");
    scanf("%i", &option);

    switch(option){
        case 1:{
            FILE* read = fopen("student_read.txt", "r");
            if (read == NULL){
                printf("failed to open file\n");
                return -1;
            }
            // 读取ID
            fscanf(read, "%s", student.studentId);
            // 吃掉ID行末尾的换行符
            fgetc(read);
            // 读取整行姓名
            fgets(student.studentName, STRING_LENGTH, read);
            // 移除姓名末尾的换行符
            student.studentName[strlen(student.studentName) - 1] = '\0';
            // 姓名转小写
            str_to_lower(student.studentName);
            // 读取年龄
            fscanf(read, "%s", student.studentAge);
            
            fclose(read);
            print_student(student);
        }
        break;
        case 2:{
            printf("\nStudent id: ");
            scanf("%s", student.studentId);
            getchar();

            char name[STRING_LENGTH] = {0};
            printf("\nFull name: ");
            fgets(name, STRING_LENGTH, stdin);
            name[strlen(name)- 1] = 0;
            str_to_lower(name);
            strcpy(student.studentName, name);

            printf("\nAge: ");
            scanf("%s", student.studentAge);
        }
        break;
        case 3:{
            printf("Program closing");
        }
        break;
        default:
            printf("Invalid Option... Try again");
    }
    return 0;
}

其他可选方案

如果你不想用fgets,也可以直接修改fscanf的格式符实现读取带空格的内容:将读取姓名的语句改为fscanf(read, " %[^\n]", student.studentName),%[^\n]表示匹配所有非换行符的字符,前面的空格用于吃掉之前残留的换行符。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.26 08:15:07