devodid
devodid

Reputation: 13

ifstream getline issue (it only reads the first line)

Something is definitely wrong with my loop because after reading and executing the first line the programs ends.

if (infile.is_open())
{
    cout << "Input filename: ";
    cin>>filename;
    infile.open(filename.c_str());

    cout<< "Output filename: ";
    cin>>filename;
    outfile.open(filename.c_str());


    while(getline(infile,input))
    {
        string output = "";
        for(int x = 0; x < input.length(); x++)
            output += cipher(input[x]);

        cout<<output<<endl;
        outfile<<output;
    }
}

Any suggestions on how to make this work?

EDIT

Followed the suggestions and got this:

if (infile.is_open()) {

        cout << "Input filename: ";
        cin>>filename;
        infile.open(filename.c_str());
        if (!infile.is_open())
        {
        std::cout << "Failed to open the input file." << std::endl;
        return -1;
        }


        cout<< "Output filename: ";
        cin>>filename;
        outfile.open(ofilename.c_str());
        if (!outfile.is_open())
        {
        std::cout << "Failed to open the output file." << std::endl;
        return -1;
        }


        while(getline(infile,line)){

        string output = "";
        for(int x = 0; x < input.length(); x++) {

        output += cipher(input[x]);


        }

        }

BUT it still reads only the first line...everything else is working perfectly fine....just can't read anything beyond the first line..

Upvotes: 1

Views: 2741

Answers (2)

WhozCraig
WhozCraig

Reputation: 66254

So I suggest this.

  1. Write char cipher(char ch) to return enciphered input for anything. if you don't want to encipher whitespace, then don't. But always return the enciphered character or unmodifed character.

  2. Use std::transform , std::istream_iterator , and std::ostream_iterator to transform your input and output files.

  3. Check your file states at the correct times.

An example appears below:

#include <iostream>
#include <fstream>
#include <iteraor>
#include <string>
using namespace std;

char cipher(char ch)
{
    if (std::isalpha(ch))
    {
        // TODO: change ch to whatever you want here.
    }

    // but always return it, whether you changed it or not.
    return ch;
}

int main()
{
    int res = EXIT_SUCCESS;

    string in_filename, out_filename;
    cout << "Input filename: ";
    cin >> in_filename;
    cout << "Output filename: ";
    cin >> out_filename;

    // don't skip whitespace
    ifstream infile(in_filename);
    ofstream outfile(out_filename);
    if ((infile >> noskipws) && outfile)
    {
        std::transform(istream_iterator<char>(infile),
                       istream_iterator<char>(),
                       ostream_iterator<char>(outfile),
                       cipher);
    }
    else
    {
        perror("Failed to open files.");
        res = EXIT_FAILURE;
    }
    return res;
}

Upvotes: 0

LihO
LihO

Reputation: 42133

It seems that you misunderstood the point of the fstream's is_open() method, since this code:

if (infile.is_open())
{
    cout << "Input filename: ";
    cin>>filename;
    infile.open(filename.c_str());
    ...
}

checks whether the infile has been successfully opened (i.e. if either a previous call to member open succeeded or if the object was successfully constructed using the parameterized constructor,
and close has not been called since
) and in case it is open it retrieves the name of the input file from cin and opens the file.

Good start would be the program that reads from the input file line by line and writes these lines to the output file without processing them:

// retrieve the name of the input file and open it:
cout << "Input filename: ";
cin>>filename;
infile.open(filename.c_str());
if (!infile.is_open())
{
    std::cout << "Failed to open the input file." << std::endl;
    return -1;
}

// retrieve the name of the output file and open it:
cout << "Output filename: ";
cin >> filename;
outfile.open(filename.c_str());
if (!outfile.is_open())
{
    std::cout << "Failed to open the output file." << std::endl;
    return -1;
}

std::string line;
while(getline(infile,line))
{
    std::cout << line << std::endl;
    outfile << line;
}

Upvotes: 1

Related Questions