| | |
While loop not ending when reading from file
Please support our C++ advertiser: Intel Parallel Studio Home
![]() |
•
•
Join Date: Jun 2004
Posts: 2,108
Reputation:
Solved Threads: 18
I have a program that reads from a file, but for some reason it never reaches the end of the file or something, because the loop never ends. I put only 2 lines of text in the file, and a loop like this still ran infinite:
Here is the full code:
Implementation:
You probably don't need to see the header file I created, but if you need to, then let me know.
C++ Syntax (Toggle Plain Text)
while (! my_file.eof())
Here is the full code:
Implementation:
C++ Syntax (Toggle Plain Text)
//-include the DebitCard implementation #include "Card.h" //-include the header for I/O #include <iostream> //-include header for files #include <fstream> #include <string> //-using definitions //-used as a shortcut using std::cout; using std::cin; using std::endl; /**main() *-definition of this file *-goes in the main method *-main method allows the *-program to be run **/ int main() { DebitCard dc; //-char array for filename char filename[50]; //-double for read amount double my_double = 0; //-char array to hold the information read char info[50]; //-declaration of file object ifstream my_file; //-prompt the user cout << "Enter The File --> "; //-get the filename from the user cin.getline(filename, sizeof(filename)); //-open the file based on the input my_file.open(filename); //-keep count of lines int count = 1; //-loop while it's no the end of the file while (! my_file.eof()) { //-get the line from file my_file.getline(info,sizeof(info)); //-store the value in a double //-this must be converted my_double = atof(info); //-if count is one, then we are on //-the first line and it is the balance //-to set the debit card to. if (count == 1) { //-print out the balance cout << "The Starting Balance Was --> " << my_double << endl; //-set the balance dc.set_balance(my_double); } else { //-variable for what should be withdrew double actual_amount = my_double; //-call the withdraw method dc.withdraw_from(my_double, actual_amount); //-if the actual amount withdrew is zero, //-then there was a problem if (actual_amount == 0) { //-show the user there was a problme cout << "Debit of $" << my_double << " -- Insufficent Funds" << endl; } else { //-show the user it was successfull. cout << "Debit of $" << my_double << " Completed" << endl; } } } //-close the file since we are done my_file.close(); //-print the final balance of the card //-use the get_balance() method cout << "The Final Balance Is $" << dc.get_balance() << endl; }
You probably don't need to see the header file I created, but if you need to, then let me know.
>while (! my_file.eof())
That's wrong. The eof member function wasn't designed to be used as a loop condition. Change it to this:
Aside from that, there's nothing wrong with your code. It works perfectly on three of my compilers. Trim the code down as much as you can such that the problem still exists. Then give us the trimmed code, a sample file that causes the problem, and details about your OS and compiler.
Haven't I told you that before concerning the exact same problem?
That's wrong. The eof member function wasn't designed to be used as a loop condition. Change it to this:
C++ Syntax (Toggle Plain Text)
while (my_file.getline(info,sizeof(info)))
Haven't I told you that before concerning the exact same problem?
I'm here to prove you wrong.
•
•
Join Date: Jun 2004
Posts: 2,108
Reputation:
Solved Threads: 18
•
•
•
•
Originally Posted by iamthwee
One other thing, if ur using c++ u should try using strings instead of chars - it shud b familiar coming from a java background
•
•
•
•
And try to avoid !EOF at all costs when reading files, u'll thank me 4 it later.
>The strod() wouldn't work with strings.
Sure it does:
I wouldn't recommend using anything but a null pointer for the second argument though. The C-style string produced by c_str() is transient and it's far too easy to invalidate any pointers to it, so you're better off not even trying unless you can quote relevant parts of the standard from memory.
A better option would be stringstreams:
>You and Narue both warned me, but I have no clue why...
The eof flag for a stream is set only after you've tried and failed to read from the stream. So let's say you use this code to read from a file:
And the contents of the file are:
Well, the first three strings are read and printed, just like you expect. However, when getline reads "test", you would expect the loop to stop because it's the last string, right? But it doesn't because getline didn't fail with an end-of-file error, it terminated successfully by reading a line. So the loop continues one more time. This is a classic off-by-one error, and it can be especially frustrating when you end up processing the last record in a file twice.
The solution is to use getline's return value as the condition for the loop. That way when getline does fail, it stops the loop at the right time because if getline fails on end-of-file (or an error), execution won't already be in the body of the loop:
Now, you can use eof() (or feof()) for a loop condition if you carefully add a kludge to the loop that protects you from the bug, but that's extra work for no real gain.
Sure it does:
C++ Syntax (Toggle Plain Text)
strtod ( s.c_str(), 0 );
A better option would be stringstreams: C++ Syntax (Toggle Plain Text)
#include <iostream> #include <string> #include <sstream> template <typename T> T jsw_strtot ( const std::string& s ) { std::istringstream iss ( s ); T ret; iss>> ret; return ret; } int main() { std::string s = "123.456"; double d = jsw_strtot<double> ( s ); std::cout<< d <<'\n'; }
The eof flag for a stream is set only after you've tried and failed to read from the stream. So let's say you use this code to read from a file:
C++ Syntax (Toggle Plain Text)
#include <iostream> #include <fstream> #include <string> int main() { std::ifstream in ( "test" ); std::string s; while ( !in.eof() ) { std::getline ( in, s ); std::cout<< s <<'\n'; } }
C++ Syntax (Toggle Plain Text)
This is a test
The solution is to use getline's return value as the condition for the loop. That way when getline does fail, it stops the loop at the right time because if getline fails on end-of-file (or an error), execution won't already be in the body of the loop:
C++ Syntax (Toggle Plain Text)
#include <iostream> #include <fstream> #include <string> int main() { std::ifstream in ( "test" ); std::string s; while ( std::getline ( in, s ) ) std::cout<< s <<'\n'; }
I'm here to prove you wrong.
•
•
•
•
Originally Posted by server_crash
It was actually my first choice to use strings. I would MUCH rather use them over char arrays, but all in all it was good practice, I guess. The reason I used char arrays is because it's the only way I could get it to convert to a double. The strod() wouldn't work with strings.
Out of curiosity, why do you say that? You and Narue both warned me, but I have no clue why... I thought it was customary to do this. The example I'm reading from actually shows to use !eof.
And I find it difficult to imagine that the string class cannot convert to double, so much so that u have to use chars? Do sum research and i'm sure u will find sumthing good about converting strings to ints and doubles :lol:
*Voted best profile in the world*
![]() |
Similar Threads
- RE: reading .wav file and putting ito inot the array (C)
- Reading from text file into array (C++)
- Reading a text file (C++)
- Reading .dat file (Visual Basic 4 / 5 / 6)
- Reading an input file as a class memeber function (C++)
- reading txt file into array (C++)
- Not reading in entire file. (C++)
Other Threads in the C++ Forum
- Previous Thread: New Lines in Visual C++ Multiline Edit Boxes?
- Next Thread: conversion to binary
| Thread Tools | Search this Thread |
api array based beginner binary bitmap c++ c/c++ calculator char char* class code coding compile compiler console conversion count database delete deploy desktop developer dll download dynamic dynamiccharacterarray email encryption error file forms fstream function functions game givemetehcodez google graph gui homeworkhelp homeworkhelper iamthwee ifstream input int integer java lib linkedlist linker list loop looping loops map math memory multiple news node number numbertoword output parameter pointer problem program programming project python random read recursion recursive reference rpg sorting string strings struct temperature template test text text-file tree unix url variable vector video visualstudio win32 windows winsock word wordfrequency wxwidgets






