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

C++文件读写实现:读取分号分隔的Student类数据最优方法

读取分格式学生数据的C++最优实现方案

首先先修正你给出的Student类语法问题(成员变量mark末尾缺分号):

#include <string>
using namespace std; // 示例简洁性使用,实际开发可根据需求省略

class Student
{
public:
    string fName;
    string sName;
    int mark; // 补上语法要求的分号
};

核心实现思路是逐行读取文件内容,按分号分割每行数据,解析为Student对象——这种方式既高效(无需一次性加载大文件到内存),又能灵活处理格式异常,是这类场景下的最优选择:

1. 字符串分割工具函数

C++标准库没有内置字符串分割函数,我们实现一个轻量版本专门处理分号分隔场景,同时自动过滤字段前后的空白字符:

#include <vector>
#include <sstream>

vector<string> split(const string& s, char delimiter) {
    vector<string> tokens;
    string token;
    istringstream tokenStream(s);
    while (getline(tokenStream, token, delimiter)) {
        // 清除字段前后的空格、制表符
        size_t start = token.find_first_not_of(" \t");
        size_t end = token.find_last_not_of(" \t");
        if (start != string::npos) {
            token = token.substr(start, end - start + 1);
        } else {
            token.clear();
        }
        if (!token.empty()) {
            tokens.push_back(token);
        }
    }
    return tokens;
}

2. 文件读取与解析逻辑

用std::ifstream逐行读取文件,搭配分割函数解析数据,同时加入完整的错误检查,避免因单条数据错误导致程序崩溃:

#include <fstream>
#include <iostream>
#include <stdexcept>
#include <vector>

vector<Student> readStudentsFromFile(const string& filePath) {
    vector<Student> students;
    ifstream file(filePath);
    if (!file.is_open()) {
        throw runtime_error("无法打开文件: " + filePath);
    }

    string line;
    int lineNum = 0;
    while (getline(file, line)) {
        lineNum++;
        vector<string> parts = split(line, ';');
        // 检查每行是否包含3个有效字段
        if (parts.size() != 3) {
            cerr << "警告: 第" << lineNum << "行格式错误,跳过该行" << endl;
            continue;
        }

        Student stu;
        stu.fName = parts[0];
        stu.sName = parts[1];
        // 字符串转int并做有效性检查
        try {
            size_t pos;
            stu.mark = stoi(parts[2], &pos);
            if (pos != parts[2].size()) {
                throw invalid_argument("包含非数字字符");
            }
        } catch (const exception& e) {
            cerr << "警告: 第" << lineNum << "行成绩解析失败: " << e.what() << ",跳过该行" << endl;
            continue;
        }

        students.push_back(stu);
    }

    file.close();
    return students;
}

3. 测试示例

在主函数中调用上述函数,验证读取结果:

int main() {
    try {
        vector<Student> students = readStudentsFromFile("file.txt");
        cout << "成功读取" << students.size() << "条学生数据:" << endl;
        for (const auto& stu : students) {
            cout << "名: " << stu.fName << ",姓: " << stu.sName << ",成绩: " << stu.mark << endl;
        }
    } catch (const exception& e) {
        cerr << "错误: " << e.what() << endl;
        return 1;
    }
    return 0;
}

方案优势说明

  • 内存高效:逐行读取模式,即使处理超大文件也不会占用过多内存
  • 鲁棒性强:覆盖文件打开失败、行格式错误、数值转换失败等多种异常场景,保证程序容错性
  • 灵活性高:分割函数可快速适配其他分隔符或空白处理规则,无需大改核心逻辑
  • 标准兼容性:完全依赖C++标准库组件,无第三方依赖,移植性强

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.19 13:50:21