Why does reading a record struct fields from std::istream fail, and how can I fix it?

后端 未结 9 2144
野性不改
野性不改 2020-11-21 11:40

Suppose we have the following situation:

  • A record struct is declared as follows

struct Person {
    unsigned int id;
    std::st         


        
9条回答
  •  暗喜
    暗喜 (楼主)
    2020-11-21 12:13

    A solution would be to read in the first entry into an ID variable.
    Then read in all the other words from the line (just push them in a temporary vector) and construct the name of the individual with all the elements, except the last entry which is the Age.

    This would allow you to still have the Age on the last position but be able to deal with name like "J. Ross Unusual".

    Update to add some code which illustrates the theory above:

    #include 
    #include 
    #include 
    #include 
    #include 
    #include 
    #include 
    
    struct Person {
        unsigned int id;
        std::string name;
        int age;
    };
    
    int main()
    {
        std::fstream ifs("in.txt");
        std::vector persons;
    
        std::string line;
        while (std::getline(ifs, line))
        {
            std::istringstream iss(line);
    
            // first: ID simply read it
            Person actRecord;
            iss >> actRecord.id;
    
            // next iteration: read in everything
            std::string temp;
            std::vector tempvect;
            while(iss >> temp) {
                tempvect.push_back(temp);
            }
    
            // then: the name, let's join the vector in a way to not to get a trailing space
            // also taking care of people who do not have two names ...
            int LAST = 2;
            if(tempvect.size() < 2) // only the name and age are in there
            {
                LAST = 1;
            }
            std::ostringstream oss;
            std::copy(tempvect.begin(), tempvect.end() - LAST,
                std::ostream_iterator(oss, " "));
            // the last element
            oss << *(tempvect.end() - LAST);
            actRecord.name = oss.str();
    
            // and the age
            actRecord.age = std::stoi( *(tempvect.end() - 1) );
            persons.push_back(actRecord);
        }
    
        for(std::vector::const_iterator it = persons.begin(); it != persons.end(); it++)
        {
            std::cout << it->id << ":" << it->name << ":" << it->age << std::endl;
        }
    }
    

提交回复
热议问题