By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
454,507 Members | 1,758 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 454,507 IT Pros & Developers. It's quick & easy.

FILESTREAM HELP NEEDED

P: n/a
#include<fstream>
using namespace std;

int main()
{
ifstream in;
ofstream out;
int a=0;
in.open("a.txt");
out.open("b.txt");
while(!in.eof())
{
in>>a;
out<<a<<endl;
}
return 0;
}

a.txt contains:

1
2
3
4
5
6
7
8

b.txt contains at the end of the program:

1
2
3
4
5
6
7
8
8

Instead of:

1
2
3
4
5
6
7
8

How can i prevent 8 from printing twice?

Nov 22 '05 #1
Share this Question
Share on Google+
18 Replies


P: n/a

"coinjo" <co****@gmail.com> wrote in message
news:11**********************@g49g2000cwa.googlegr oups.com...
#include<fstream>
using namespace std;

int main()
{
ifstream in;
ofstream out;
int a=0;
in.open("a.txt");
out.open("b.txt");
while(!in.eof())
{
in>>a;
out<<a<<endl;
}
return 0;
}


First, you should be following the advice "mlimber" gave to your previous
post:

Pass the filenames to the constructors of the stream objects, instead of
calling open explicitly.

Then, pust the input statement in your while condition, not eof(). Using
eof() in your while statement is incorrect, since it does not detect the end
of file until _after_ it fails to read. The eof() test should be used
_after_ a read fails, to detect if the _reason_ for the read failure was an
end-of-file (as opposed to some other unexpected condition).

This is undoubtedly the cause of your problem. If there's a blank line at
the end of your text file (which there often is, because whoever enters the
data usually hits Enter after each line), then the last time through the
loop, it tries to read a blank line into an integer, which fails. Since the
read failed, the variable a still contains what it did before, which is the
value 8. So, you output 8.

-Howard

Nov 22 '05 #2

P: n/a

coinjo wrote:
#include<fstream>
using namespace std;

int main()
{
ifstream in;
ofstream out;
int a=0;
in.open("a.txt");
out.open("b.txt");
while(!in.eof())
{
in>>a;
out<<a<<endl;
}
The eof() method tells you if the *last* input operation attempted to
read past the EOF, not if the *next* input operation will read past the
EOF, so your loop executes one too many times. Here's how the last
three iterations go:

1. Test for EOF
2. Not at EOF, so read next character
3. Next character read was 8, assign to a
4. Write contents of a to out
5. Test for EOF
6. Not at EOF, so read the next character
7. Next character read was EOF, so read fails; a is left unchanged
8. Write contents of a to out
9. Test for EOF
10. At EOF, exit loop

Instead of testing on in.eof(), test on the result of the input
operator:

while (in >> a)
{
out << a << endl;
}
if (in.eof())
{
cerr << "hit end of file" << endl;
}
else
{
cerr << "some other error" << endl;
}
return 0;
}


Nov 22 '05 #3

P: n/a

"Howard" <al*****@hotmail.com> wrote in message
news:OA*******************@bgtnsc05-news.ops.worldnet.att.net...
This is undoubtedly the cause of your problem. If there's a blank line at
the end of your text file (which there often is, because whoever enters
the data usually hits Enter after each line), then the last time through
the loop, it tries to read a blank line into an integer, which fails.
Since the read failed, the variable a still contains what it did before,
which is the value 8. So, you output 8.


Come to think of it, it will behave this way even if there's _not_ an extra
line at the end, because the last successful read (of the value 8 into a)
will still not have set the eof flag. That flag only gets set after a
failure to read occurs.

-Howard
Nov 22 '05 #4

P: n/a
In message <11**********************@g49g2000cwa.googlegroups .com>,
coinjo <co****@gmail.com> writes
[...]
while(!in.eof())

How can i prevent 8 from printing twice?

By reading TFFAQ:

http://www.parashift.com/c++-faq-lit....html#faq-15.5

--
Richard Herring
Nov 22 '05 #5

P: n/a
coinjo wrote:
#include<fstream>
using namespace std;

int main()
{
ifstream in;
ofstream out;
int a=0;
in.open("a.txt");
out.open("b.txt");
while(!in.eof())
{
in>>a;
out<<a<<endl;
}
return 0;
}


It's one of the mysteries of the universe, why does every single newbie
make the mistake that coinjo made? Coinjo I'd really appreciate it if
you told me why you wrote 'while (!in.eof())' in your code. Did you read
it in a book? Did it just seem right? If I can understand why you wrote
the code like that, I'll be better able to help the next newbie here who
has made the same mistake.

Thanks,
John
Nov 22 '05 #6

P: n/a
John Harrison <jo*************@hotmail.com> wrote:
coinjo wrote:
#include<fstream>
using namespace std;

int main()
{
ifstream in;
ofstream out;
int a=0;
in.open("a.txt");
out.open("b.txt");
while(!in.eof())
{
in>>a;
out<<a<<endl;
}
return 0;
}


It's one of the mysteries of the universe, why does every single newbie
make the mistake that coinjo made? Coinjo I'd really appreciate it if
you told me why you wrote 'while (!in.eof())' in your code. Did you read
it in a book? Did it just seem right? If I can understand why you wrote
the code like that, I'll be better able to help the next newbie here who
has made the same mistake.


I am not coinjo, but I have a guess. Maybe people are trying to emulate
the C idiom of:

int c;
FILE* fp = fopen("file", "r");
while ((c = getc(fp) != EOF) {
/* ... */
}

If this came out of a book, my guess is that some book authors who write
C++ books really don't know C++, but C, and just do things the C way
with minor changes to try and make it look like C++.

--
Marcus Kwok
Nov 22 '05 #7

P: n/a
John Harrison <jo*************@hotmail.com> wrote:
coinjo wrote:
#include<fstream>
using namespace std;

int main()
{
ifstream in;
ofstream out;
int a=0;
in.open("a.txt");
out.open("b.txt");
while(!in.eof())
{
in>>a;
out<<a<<endl;
}
return 0;
}


It's one of the mysteries of the universe, why does every single newbie
make the mistake that coinjo made? Coinjo I'd really appreciate it if
you told me why you wrote 'while (!in.eof())' in your code. Did you read
it in a book? Did it just seem right? If I can understand why you wrote
the code like that, I'll be better able to help the next newbie here who
has made the same mistake.


I am not coinjo, but I have a guess. Maybe people are trying to emulate
the C idiom of:

int c;
FILE* fp = fopen("file", "r");
while ((c = getc(fp)) != EOF) {
/* ... */
}

If this came out of a book, my guess is that some book authors who write
C++ books really don't know C++, but C, and just do things the C way
with minor changes to try and make it look like C++.

--
Marcus Kwok
Nov 22 '05 #8

P: n/a

"Marcus Kwok" <ri******@gehennom.net> wrote in message
news:dl**********@news-int.gatech.edu...
John Harrison <jo*************@hotmail.com> wrote:
coinjo wrote:
#include<fstream>
using namespace std;

int main()
{
ifstream in;
ofstream out;
int a=0;
in.open("a.txt");
out.open("b.txt");
while(!in.eof())
{
in>>a;
out<<a<<endl;
}
return 0;
}
It's one of the mysteries of the universe, why does every single newbie
make the mistake that coinjo made? Coinjo I'd really appreciate it if
you told me why you wrote 'while (!in.eof())' in your code. Did you read
it in a book? Did it just seem right? If I can understand why you wrote
the code like that, I'll be better able to help the next newbie here who
has made the same mistake.


I am not coinjo, but I have a guess. Maybe people are trying to emulate
the C idiom of:

int c;
FILE* fp = fopen("file", "r");
while ((c = getc(fp)) != EOF) {
/* ... */
}


This isn't really different from the way it's done with
C++ streams. The above snippet also checks for EOF after
reading, not before.

If this came out of a book, my guess is that some book authors who write
C++ books really don't know C++, but C, and just do things the C way
with minor changes to try and make it look like C++.


IMO with respect to this issue, the 'C way' and 'C++ way' are
the same (check EOF after reading, not before).

-Mike
Nov 22 '05 #9

P: n/a
Mike Wahler wrote:

"Marcus Kwok" <ri******@gehennom.net> wrote in message
news:dl**********@news-int.gatech.edu... >John Harrison
<jo*************@hotmail.com> wrote:
coinjo wrote: while(!in.eof())
{
in>>a;
out<<a<<endl;
}
return 0;
> }
I am not coinjo, but I have a guess. Maybe people are trying to
emulate the C idiom of:

int c;
FILE* fp = fopen("file", "r");
while ((c = getc(fp)) != EOF) {
/* ... */
}


This isn't really different from the way it's done with
C++ streams. The above snippet also checks for EOF after
reading, not before.


Right, the C++ example shown above actually is closer to:

while(!feof(fp))
{
}

Which gives the same sort of error.

Brian

Nov 22 '05 #10

P: n/a
John Harrison wrote:
It's one of the mysteries of the universe, why does every single newbie
make the mistake that coinjo made? Coinjo I'd really appreciate it if
you told me why you wrote 'while (!in.eof())' in your code. Did you read
it in a book? Did it just seem right? If I can understand why you wrote
the code like that, I'll be better able to help the next newbie here who
has made the same mistake.


My guess is that it's two reasons:

1. The textual description is "While we're not at the end of file, do
something". This is an accurate description, but does not map cleanly
onto the C FILE* idiom or the C++ istream idiom.

2. It's a Pascal-ism. Instructors today probably learned on Pascal,
which did use that idiom:

while not eof(file) do
(* read your data and process *)
end;
Nov 22 '05 #11

P: n/a
It just seems right to me. Please help me!

Nov 22 '05 #12

P: n/a

coinjo wrote:
It just seems right to me. Please help me!


Lot's of people have given an explanation and the answer, including a
link to the FAQ

http://www.parashift.com/c++-faq-lit....html#faq-15.5

Have you tried what's been suggested? If so and it's still not working,
post the new code so people can look at it.

Or do you not understand what's been suggested? If that's the case,
explain what it is that you're not clear on and someone can try and
give you another explanation.

Gavin Deane

Nov 22 '05 #13

P: n/a
In message <11**********************@f14g2000cwb.googlegroups .com>,
coinjo <co****@gmail.com> writes
It just seems right to me. Please help me!

Already did.

Your problem is that eof() doesn't mean what you think it means.
You want it to mean "you have reached at the end of the file", but it
actually says "you have tried to read _beyond_ the end of the file". So
you need to test the file state after reading, not before.

--
Richard Herring
Nov 22 '05 #14

P: n/a
"coinjo" <co****@gmail.com> wrote in message
news:11**********************@f14g2000cwb.googlegr oups.com...
It just seems right to me. Please help me!


It's already been explained to you with a way to fix it. Another quick fix
is:

int main()
{
ifstream in("a.txt");
ofstream out("b.txt");
while(!in.eof())
{
in>>a;
if ( !in.eof() )
out<<a<<endl;
}
return 0;
}

Does that make more sense what the problem is? eof() is not set to true
until AFTER the input is read. but you are reading the input, and writing
it. But the input could of failed because end of file was reached. So
either change the logic as suggested before, or put in another test for
eof() there.

How it actually SHOULD be:

int main()
{
ifstream in("a.txt");
ofstream out("b.txt");
while( in>>a )
{
out<<a<<endl;
}
return 0;
}

in >> a returns false (I believe) when eof() is reached or some other error
has occured.
Nov 22 '05 #15

P: n/a
>> "Marcus Kwok" <ri******@gehennom.net> wrote in message
> I am not coinjo, but I have a guess. Maybe people are trying to
> emulate the C idiom of:
>
> int c;
> FILE* fp = fopen("file", "r");
> while ((c = getc(fp)) != EOF) {
> /* ... */
> }
Mike Wahler wrote:
This isn't really different from the way it's done with
C++ streams. The above snippet also checks for EOF after
reading, not before.

Default User <de***********@yahoo.com> wrote: Right, the C++ example shown above actually is closer to:

while(!feof(fp))
{
}

Which gives the same sort of error.


Sorry, yes, this is what I meant.

--
Marcus Kwok
Nov 22 '05 #16

P: n/a

"red floyd" <no*****@here.dude> wrote in message
news:dJ*****************@newssvr13.news.prodigy.co m...
John Harrison wrote:
It's one of the mysteries of the universe, why does every single newbie
make the mistake that coinjo made? Coinjo I'd really appreciate it if you
told me why you wrote 'while (!in.eof())' in your code. Did you read it
in a book? Did it just seem right? If I can understand why you wrote the
code like that, I'll be better able to help the next newbie here who has
made the same mistake.


My guess is that it's two reasons:

1. The textual description is "While we're not at the end of file, do
something". This is an accurate description, but does not map cleanly
onto the C FILE* idiom or the C++ istream idiom.

2. It's a Pascal-ism. Instructors today probably learned on Pascal,
which did use that idiom:

while not eof(file) do
(* read your data and process *)
end;


Correct, at least in my experience. My college courses mostly used Pascal
to teach programming, and both the algorithms and the code examples used
were phrased in that "while not eof" form. I also used that form when I
first returned to C++ (from Delphi), and was quickly corrected - in this
very forum. Since we don't have a way to stop posters and give them this
info before they ask, the best thing is to just take it in stride, point out
their mistake (gently), and guide them to the FAQs.

-Howard
-Howard

Nov 22 '05 #17

P: n/a

"Jim Langston" <ta*******@rocketmail.com> wrote in message
news:74******************@fe03.lga...
"coinjo" <co****@gmail.com> wrote in message
news:11**********************@f14g2000cwb.googlegr oups.com...
It just seems right to me. Please help me!
It's already been explained to you with a way to fix it. Another quick
fix is:

int main()
{
ifstream in("a.txt");
ofstream out("b.txt");
while(!in.eof())
{
in>>a;
if ( !in.eof() )
out<<a<<endl;
}
return 0;
}

Does that make more sense what the problem is? eof() is not set to true
until AFTER the input is read. but you are reading the input, and writing
it. But the input could of failed because end of file was reached. So
either change the logic as suggested before, or put in another test for
eof() there.

How it actually SHOULD be:

int main()
{
ifstream in("a.txt");
ofstream out("b.txt");
while( in>>a )
{
out<<a<<endl;
}
return 0;
}

in >> a returns false (I believe)


Yes.
when eof() is reached or some other error has occured.


Yes. Which is why it's common at the end of such loops
to distinguish between eof and error:

while(in >> a)
{
}
if(!in.eof())
; // trouble
else
; // eof

-Mike
Nov 22 '05 #18

P: n/a
It is ok now thanks.

Nov 22 '05 #19

This discussion thread is closed

Replies have been disabled for this discussion.