简体   繁体   中英

Storing 4 values from each line from a txt file, into an object - C++

I'm wanting to take 4 values, each separated by a comma, and store them to a airport object. Each line would have those 4 values would be stored together. So, calling all objects from Sweden, would find all objects from the country sweden and retrieve the appropriate values as well. Right now I have 4 different vectors, which store all 4 object values, however, doesn't necessarily set all 4 attributes/values together as an object. Help is greatly appreciated.

Examples of what the Text File looks like -

1,Goroka,Goroka,Papua New Guinea,GKA,AYGA,-6.081689,145.391881,5282,10,U 2,Madang,Madang,Papua New Guinea,MAG,AYMD,-5.207083,145.7887,20,10,U


#include "pch.h"
#include <iostream>
#include <fstream>
#include <vector>
#include <string>
#include <iterator>
#include <algorithm>
using namespace std;

struct Airport
{
string code;
string name;
string city;
string nation;

friend std::istream& operator>>(std::istream& input, Airport& a);
};

istream& operator>>(std::istream& input, Airport& a)
 {
getline(input, a.code, ',');
getline(input, a.name, ',');
getline(input, a.city, ',');
getline(input, a.nation);
return input;
}
////////////////////////////////////////////

vector<string> split(const string& s, const string& delim)
 {
const bool keep_empty = true;
vector<string> result;

if (delim.empty())
{
    result.push_back(s);
    return result;
}

string::const_iterator substart = s.begin(), subend;

while (true)
{
    subend = search(substart, s.end(), delim.begin(), delim.end());
    string temp(substart, subend);
    if (keep_empty || !temp.empty())
    {
        result.push_back(temp);
    }
    if (subend == s.end())
    {
        break;
    }
    substart = subend + delim.size();
}

return result;
}

// Sorting Function 
bool Sort_By_Name_Ascending(const Airport& a, const Airport& b)
{
return a.name < b.name;
}


int main()
{
vector<Airport> database;
Airport a;

char choice;
string chr;

ifstream inputFile;
inputFile.open("airports.dat");

if (!inputFile)
{
    cout << "File Access Error!";
    return 0;
}

string fileLine;
cout << "Reading File ..." << endl;

while (!inputFile.eof())
{
    getline(inputFile, fileLine);
    vector<string> lineVector = split(fileLine, ",");
    if (lineVector[4].length() == 3)
    {
        while (inputFile >> a)
        {
            database.push_back(a);
        }
    }

}

cout << "What would you like to do?\nA. Sort in Alphabetical Order.\nB. 
Delete an Airport.\nC. Exit Program." << endl;

cin >> choice;

switch (choice)
{
case 'A':
    sort(database.begin(), database.end(), Sort_By_Name_Ascending);
break;

case 'B':
    cout << "Deleting a value" << endl;

break;

case 'C':
return 0;
break;
}


return 0;
}

You may want to organize your data structures to model the input data:

struct Airport
{
  std::string    code;
  std::string    name;
  std::string    city;
  std::string    nation;
};

A next step is to overload operator>> to read in an instance from a stream:

struct Airport
{
  //...
  friend std::istream& operator>>(std::istream& input, Airport& a);
};
std::istream& operator>>(std::istream& input, Airport& a)
{
    std::getline(input, a.code, ',');
    std::getline(input, a.name, ',');
    std::getline(input, a.city, ',');
    std::getline(input, a.nation);
    return input;
}

This simplifies the input:

std::vector<Airport> database;
Airport a;
while (inputfile >> a)
{
  database.push_back(a);
}

To sort, you can come up with some functions or function objects and supply them to std::sort :

bool Sort_By_Name_Ascending(const Airport& a, const Airport& b)
{
  return a.name < b.name;
}

//...
std::sort(database.begin(), database.end(), Sort_By_Name_Ascending);

Edit 1: The whole record or line
There is a difference between modeling the whole line versus only fields you are interested in. If your records are text line (one record == one text line), you may want to read in the text line as a string then extract the fields you are interested in.

std::istream& operator>>(std::istream& input, Airport& a)
{
    std::string record;
    std::getline(input, record);

    // Now extract the interesting fields from the string.
    std::istringstream record_stream;
    unsigned int record_number;
    char         comma;
    record_stream >> record_number;  // Read but ignore.
    record_stream >> comma;          // Read but ignore.
    std::getline(record_stream, a.code, ',');
    std::getline(record_stream, a.name, ',');
    std::getline(record_stream, a.city, ',');
    std::getline(record_stream, a.nation);
    return input;    
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM