Solved

fstream variable issue

Posted on 2011-03-14
12
325 Views
Last Modified: 2012-06-27
Hi,
Do you know why the last value on my file is being printed twice?

Thanks for your help. data.txt
#include<iostream>
#include<fstream>

using namespace std;

int main(){
	ifstream f;
	f.open("data.txt");
	int x=0;
	while(!f.eof())
	{f>>x;
	cout<<x<<' ';
	cout<<endl;
	}


return 0;
}

Open in new window

0
Comment
Question by:pgmerLA
  • 4
  • 4
  • 4
12 Comments
 
LVL 53

Expert Comment

by:Infinity08
ID: 35130621
>> Do you know why the last value on my file is being printed twice?

Because the end of the file is not reached until after trying to read past it.

The last line is read from the file, but it doesn't set the eof flag yet, so the code tries to read another entry, and that fails, so the eof flag is set, but you don't check the eof flag before printing out the data.

Either check eof before the cout (and end the loop if it's set), or use a line based approach by using getline to read the file one line at a time :

        http://www.cplusplus.com/reference/string/getline/
0
 
LVL 33

Expert Comment

by:sarabande
ID: 35130708
you could simply code like

   if (f>>x)
      cout<<x<<endl;

note the additional space makes not so much sense if you do a new line after.

Sara
0
 

Author Comment

by:pgmerLA
ID: 35130936
Hi Infinity08, could you write me a sample code?

Thanks.
0
Announcing the Most Valuable Experts of 2016

MVEs are more concerned with the satisfaction of those they help than with the considerable points they can earn. They are the types of people you feel privileged to call colleagues. Join us in honoring this amazing group of Experts.

 

Author Comment

by:pgmerLA
ID: 35130951
Hi Sara,

how would I know it's the end of the file?
Can I use that for a very very long file?
0
 
LVL 33

Assisted Solution

by:sarabande
sarabande earned 250 total points
ID: 35131159
the f>>x would fail on eof. the problem is it also will fail if it reads not an integer.

to make it really safe you should apply infinity08's advice and read with getline. after that use istringstream to retrieve the integers:

      
ifstream f("data.txt");
	int x=0;
                     std::string s;
	while(getline(f, s))
	{
                            std::istringstream is(s); // seed with textline
                            while (is>>x)
	            cout<<x<<endl;
	}

Open in new window


the above would read the whole textfile line by line. if a line contains alphabetics all numbers after were ignored, but the outer while loop doesn't stop, if not using stringstream the first non-integer would make the f stream fail and no further operation nor the check on f.eof() would succeed after. that means the loop goes infinite.

Sara
0
 
LVL 33

Expert Comment

by:sarabande
ID: 35131187
yes you could use it for long textfiles as well. but you probably will do somewhat with the x numbers.

Sara
0
 
LVL 53

Expert Comment

by:Infinity08
ID: 35131257
>> Hi Infinity08, could you write me a sample code?

What would you like a sample code for ?

Do you understand what the issue is in your original code ? If not, please let me know which part of my explanation requires clarification, and I'll be happy to provide it.
0
 

Author Comment

by:pgmerLA
ID: 35131413
I understand the issue.
Could you write me an example for : "Either check eof before the cout (and end the loop if it's set)"
Would I use a do..while loop in that case?
0
 
LVL 53

Accepted Solution

by:
Infinity08 earned 250 total points
ID: 35131758
You need to check if the eof flag was set after reading the data, but before trying to use the data. However you want to do that, works.

But what I was alluding to, was :

        while(!f.eof())
        {
            f>>x;
            if (f.eof()) break;
            cout<<x<<' ';
            cout<<endl;
        }

However, that still doesn't take care of all possible error cases, so I still recommend using getline to read the file line by line in a loop.
0
 

Author Comment

by:pgmerLA
ID: 35131783
Thanks a lot guys!
0
 
LVL 33

Expert Comment

by:sarabande
ID: 35135575
instead of

    if (f.eof()) break;

i would suggest

   if (!f) break;

that would cover both eof and fail condition.

Sara
0
 
LVL 53

Expert Comment

by:Infinity08
ID: 35135726
That line was specifically meant to get rid of the "last value on my file is being printed twice" problem. It was not a recommendation to actually use that in production code. My recommendation for production code, is to use a line-based approach using getline (see my previous posts).
0

Featured Post

Free Tool: Port Scanner

Check which ports are open to the outside world. Helps make sure that your firewall rules are working as intended.

One of a set of tools we are providing to everyone as a way of saying thank you for being a part of the community.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Often, when implementing a feature, you won't know how certain events should be handled at the point where they occur and you'd rather defer to the user of your function or class. For example, a XML parser will extract a tag from the source code, wh…
Introduction This article is a continuation of the C/C++ Visual Studio Express debugger series. Part 1 provided a quick start guide in using the debugger. Part 2 focused on additional topics in breakpoints. As your assignments become a little more …
The goal of the video will be to teach the user the concept of local variables and scope. An example of a locally defined variable will be given as well as an explanation of what scope is in C++. The local variable and concept of scope will be relat…
The goal of the video will be to teach the user the difference and consequence of passing data by value vs passing data by reference in C++. An example of passing data by value as well as an example of passing data by reference will be be given. Bot…

856 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question