-1

I am trying to read a file having multiple lines, where each line has a word and then a space followed by a short description of the word.

Example of the text file:

hello A type of greeting
clock A device which tells us the time
.

The fullstop (.) at the end represents that there are no more lines to read.

I tried an approach using a delimiter in the getline() function, but only succeeded in reading one line of the file. I want to store the first word (before the first space) in a variable, say word, and the description (words after the first space until a new line character is encountered) in another variable, say desc.

My approach:

#include <iostream>
#include <fstream>
#include <string.h>

using namespace std;

int main()
{
    string filename = "text.txt" ;
    ifstream file (filename);
    if (!file)
    {
        cout<<"could not find/open file "<<filename<<"\n";
        return 0;
    } 

    string word;
    string desc;
    string line;


    while(file){
        getline(file,line,' ');
        
        word = line;
        break;
    }
    while(file){
        getline(file,line,'\n');
        desc = line;
        break;
    }    

   file.close();
    cout<<word<<":  ";
    cout<<desc<<"\n";

    return 0;
}

The output of the above code is:

hello:  A type of greeting

I tried adding another parent while loop to the ones written above, having the condition file.eof(), but then the program never enters the two child loops.

Remy Lebeau
  • 454,445
  • 28
  • 366
  • 620
Frexpe
  • 23
  • 5
  • to find better approach https://stackoverflow.com/questions/5605125/why-is-iostreameof-inside-a-loop-condition-i-e-while-stream-eof-cons – Build Succeeded Oct 21 '20 at 05:15
  • @buildsucceeded no, because eof is only set _after_ an unsuccessful read. But at Frexpe: have you tried using Google or the search function of this site? This question has been asked many times and there are a lot of examples online – JHBonarius Oct 21 '20 at 05:16
  • Use `while(getline(file,line,'\n')) { desc = line;}` instead. – πάντα ῥεῖ Oct 21 '20 at 05:21
  • Read a good [C++ programming book](https://stroustrup.com/programming.html) and see [this C++ reference](https://en.cppreference.com/w/cpp), perhaps also the C++11 standard [n3337](http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2012/n3337.pdf). Take inspiration from existing C++ open source projects (e.g. [GCC](http://gcc.gnu.org/) or [RefPerSys](http://refpersys.org/) or [fish](https://fishshell.com/)...). Use both [GCC](http://gcc.gnu.org/) and [GDB](https://www.gnu.org/software/gdb/) after having read their documentation – Basile Starynkevitch Oct 21 '20 at 05:29

1 Answers1

2

You don’t need multiple loops, a single loop will suffice. Read a line, and then use a std::istringstream to split it as needed. Repeat for each line.

For example:

#include <iostream>
#include <fstream>
#include <sstream>
#include <string>

using namespace std;

int main()
{
    string filename = "text.txt";
    ifstream file (filename);
    if (!file)
    {
        cout << "could not find/open file " << filename << "\n";
        return 0;
    } 

    string word;
    string desc;
    string line;

    while (getline(file, line) && (line != ".")) {
        istringstream iss(line);
        iss >> word;
        getline(iss, desc);
        cout << word << ":  " << desc << "\n";
    }

    return 0;
}

Govind Mohan
  • 89
  • 1
  • 7
Remy Lebeau
  • 454,445
  • 28
  • 366
  • 620