Разбор строк, целых и чисел из текстового файла - PullRequest
0 голосов
/ 23 июня 2019

У меня есть следующий текстовый файл:

Jean Rousseau
1001 15.50
Steve Woolston
1002 1423.20
Michele Rousseau
1005 52.75
Pete McBride
1007 500.32
Florence Rousseau
1010 1323.33
Lisa Covi
1009 332.35
Don McBride
1003 12.32
Chris Carroll
1008 32.35
Yolanda Agredano
1004 356.00
Sally Sleeper
1006 32.36

Я должен хранить строки (Жан Руссо), int s (1001) и float s (15.50) в 3 std::vectors.

У меня есть рабочее решение, но я хотел бы знать, если это правильный способ сделать это.

Мой код следующий:

int counter=0;
std::string line;
std::ifstream myfile("InFile.txt");
std::vector<std::string> names;
std::vector<int> ids;
std::vector<float> balances;
int buf_int;
float buf_float;
while(myfile) {
   std::getline(myfile, line);
   std::cout << line << std::endl;
   std::stringstream ss(line);
   if(counter%2 == 0) {
        names.push_back(line);
   }
   else {
          if(ss >> buf_int) ids.push_back(buf_int);
          if(ss >> buf_float) balances.push_back(buf_float);
   }
   counter++;
}

Пожалуйста, дайте мне знать, если есть лучший способ сделать это. Спасибо.

1 Ответ

0 голосов
/ 23 июня 2019

Как сказал πάντα ῥεῖ. Что лучше? Ваш вопрос, возможно, будет закрыт из-за запроса мнений. Тем не мение. Я хотел бы дать один альтернативный ответ, используя алгоритмы.

По моему мнению, 3 данных 'name', 'id' и 'balance' принадлежат друг другу. Поэтому я бы поместил их в структуру. (И да, я игнорирую ваше желание иметь 3 отдельных вектора. Я прошу прощения.)

И поскольку мы хотим прочитать эти данные, мы перегрузим оператор экстрактора. И оператор вставки, а также. Возможно, позже будет добавлен дополнительный функционал. Тогда будет проще.

И поскольку этих данных должно быть много, std :: vector является идеальным решением для их хранения.

Имея 3 элемента в структуре, мы можем легко прочитать все элементы вместе и затем поместить их в вектор.

И для чтения всего файла в функции main мы используем один вкладыш. Мы определяем векторную переменную с помощью конструктора диапазона.

И затем мы копируем полный вектор со всеми данными в std :: cout.

Пожалуйста, обратите внимание. Я не занимался обработкой ошибок. Это должно быть добавлено. Но это простая задача. На данный момент программа перестает читать, как только найден какой-то не соответствующий текст. Например: последняя строка должна иметь "\ n".

Пожалуйста, смотрите:

#include <iostream>
#include <vector>
#include <string>
#include <fstream>
#include <iterator>

// Name Id and balance belong together. Therefore, we put it together in one struct
struct NameIdBalance    
{
    std::string name{}; int id{0};  float balance{0.0};
    // And since we want to read this data, we overload the extractor
    friend std::istream& operator>>(std::istream& is, NameIdBalance& nid) { 
        std::getline(is, nid.name); 
        is >> nid.id >> nid.balance;   is.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
        return is;  
    }
    // For debug purposes, we also overload the inserter
    friend std::ostream& operator << (std::ostream& os, const NameIdBalance& nid) { return os << "Name: " << nid.name << " (" << nid.id << ") --> " << nid.balance; }
};

int main()
{
    // 1. Open File
    std::ifstream myfile("r:\\InFile.txt");
    // 2 Read all data into a vector of NameIdBalance
    std::vector<NameIdBalance> nameIdBalance{ std::istream_iterator<NameIdBalance>(myfile), std::istream_iterator<NameIdBalance>() };

    // For debug purposes: Print complete vector to std::cout
    std::copy(nameIdBalance.begin(), nameIdBalance.end(), std::ostream_iterator<NameIdBalance>(std::cout, "\n"));
    return 0;
}

Но есть 42 миллиона других возможных решений. , , _: -)

РЕДАКТИРОВАТЬ:

После подсказки LightnessRacesinOrbit я удалил слово POD. структура не является POD.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...