从文本文件c ++填充对象

Posted

技术标签:

【中文标题】从文本文件c ++填充对象【英文标题】:Fill object from text file c++ 【发布时间】:2020-04-10 08:23:36 【问题描述】:

我正在编写一个需要从文本文件加载数据库的程序。数据库类包含条目向量,条目是一个类。

例子

vector<People> lib;
class People 
 string name;
 string occupation;
 int cats_age[2]
 int age;
//code here

如何从包含格式化条目的文本文件中填充数据库

marry wang-dog walker-0-17-78

我尝试过使用

file.read((char*)& entry, sizeof(entry))

但是没有成功

我也考虑过重载运算符 >> 但是有些字段是包含空格的字符串。 如何通过读取字符“-”之间的所有内容来填充对象?

-谢谢

【问题讨论】:

无关:People 这个名字不好,因为它实际上只包含一个人。 【参考方案1】:

您不能将原始 read 从文件转换为 People 对象。 People 包含一个重要的类型 (std::string),文件中的每条记录都必须具有相同的大小才能使原始读取工作,而您的文件中并非如此。

人们经常做的是为operator&gt;&gt; 添加一个重载,以支持来自任何std::istream 的格式化输入(如std::ifstreamstd::cin)。

由于成员变量为private,您需要将添加的operator&gt;&gt; 设置为friend,以便它可以访问private 变量。

您可以使用std::getline 读取直到找到某个字符(例如您的分隔符-)。它将从流中删除分隔符,但不将其包含在存储结果的变量中。

std::getline 返回对 istream 的引用,以便您可以链接多个 std::getlines。

我还将您的课程重命名为 Person,因为它只包含一个人的信息。

例子:

#include <iostream>
#include <string>
#include <vector>

#include <sstream>

class Person 
    std::string name;
    std::string occupation;
    int cats_age[2];
    int age;

    friend std::istream& operator>>(std::istream&, Person&);
    friend std::ostream& operator<<(std::ostream&, const Person&);
;

// read one Person from an istream
std::istream& operator>>(std::istream& is, Person& p) 
    using std::getline;
    char del; // for reading the delimiter '-'
    std::string nl_eater; // for removing the newline after age

    // chaining getline:s and >>:s
    return getline(getline(getline(is, p.name, '-'), p.occupation, '-') >>
                       p.cats_age[0] >> del >> p.cats_age[1] >> del >> p.age, nl_eater);


// write one Person to an ostream
std::ostream& operator<<(std::ostream& os, const Person& p) 
    return os << p.name << '-' << p.occupation << '-' << p.cats_age[0] << '-'
              << p.cats_age[1] << '-' << p.age << '\n';


int main() 
    // example of an istream - it could just as well had been a std::ifstream
    std::istringstream is(
        "marry wang-dog walker-0-17-78\n"
        "foo bar-unemployed-1-2-3\n"
    );

    std::vector<Person> people;

    Person temp;
    while(is >> temp)  // loop for as long as extraction of one Person succeeds
        people.push_back(temp);
    

    // print all the collected Persons
    for(const Person& p : people) 
        std::cout << p;
    

输出:

marry wang-dog walker-0-17-78
foo bar-unemployed-1-2-3

我建议您选择与- 不同的字段分隔符。许多名称包含-,负数也是如此。使用不太可能包含在任何字段中的字符。

【讨论】:

@TedLyngmo:和往常一样,我很想用std::regex 给出我的典型答案。但是因为您的答案非常好且高效,所以我保存了工作并简单地对您的答案进行了紫外线处理。 +1

以上是关于从文本文件c ++填充对象的主要内容,如果未能解决你的问题,请参考以下文章

从 Qt 中的文本文件填充表格小部件

从文本文件填充数据集

如何用两列 C++ 从文本文件中填充向量

在c ++中从文件中读取整行

从 django 应用程序下载一个文本/csv 文件,该文件从数据库查询中填充 HTML 表

如何以不同的方式格式化不同的文本行,从在 AS3 中创建的文本字段,从 txt 文件填充文本?