Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Fstream problem

0 views
Skip to first unread message

ELIE

unread,
Mar 24, 2004, 6:23:53 PM3/24/04
to
Hi, The following is a piece of my code, i am having problems opening a file
when i have the while loop to count how many lines are there in my file
already before i write to it. I have noticed that it works when i take off
that loop, yet when i put it back on, it gives me the error "Error in
opening file".

Thanks in advance

fstream Publish("client.txt");

while (Publish.get(next))
{
if ( next == '\n' )
count++;

}

cout << count;

Publish.seekg(0, ios::end);

if (!Publish)
{
cerr << "Error in opening file" << endl;
exit(1)
}

Publish << s->ReceiveLine();

Publish.close();

}


Jacek Dziedzic

unread,
Mar 24, 2004, 7:31:40 PM3/24/04
to
Użytkownik ELIE napisał:

if(!Publish) tests if the stream is not in the good() state.
A stream failing to open is an example of such a condition,
HOWEVER it also takes place when the stream is at EOF.

You are basically at the end of file, your stream therefore is
no longer good(), which you detect, but your error message should
rather be

"something went wrong with the file or end of file was reached".

HTH,
- J.

Buster

unread,
Mar 24, 2004, 7:38:00 PM3/24/04
to
ELIE wrote:
> Hi, The following is a piece of my code, i am having problems opening a file
> when i have the while loop to count how many lines are there in my file
> already before i write to it. I have noticed that it works when i take off
> that loop, yet when i put it back on, it gives me the error "Error in
> opening file".
>
> Thanks in advance
>
> fstream Publish("client.txt");
>
> while (Publish.get(next))
> {
> if ( next == '\n' )
> count++;
>
> }

OK, but you could use getline from the <string> header. Also I'd put
this in a separate function:

unsigned count_lines (std::istream & stream)
{
unsigned count = 0;
std::string line;
while (std::getline (stream, line)) ++ count;
return count; // TODO: should make sure it was only eof
// (maybe use stream.exceptions () for this)
}

In any case, if you're here then you have exited the loop, so the
condition, Publish.get(next), must have been false; therefore,
Publish's std::ios_base::failbit is now set (on, true, 1).

>
> cout << count;
>
> Publish.seekg(0, ios::end);

This does nothing at all with Publish in a failed state. You need
to reset the stream's state first with "Publish.clear ();".
I'd be tempted to let the first fstream go out of scope here and
use a brand new one for the remainder of the function.

> if (!Publish)
> {
> cerr << "Error in opening file" << endl;
> exit(1)
> }
>
> Publish << s->ReceiveLine();
>
> Publish.close();

OK, but this is handled by the destructor. You didn't use
Publish.open (), so why be explicit here?

> }

That ought to do it.
Regards,
Buster.

Buster

unread,
Mar 24, 2004, 7:47:28 PM3/24/04
to
Buster wrote:

> OK, but you could use getline from the <string> header. Also I'd put
> this in a separate function:
>
> unsigned count_lines (std::istream & stream)
> {
> unsigned count = 0;
> std::string line;
> while (std::getline (stream, line)) ++ count;
> return count; // TODO: should make sure it was only eof
> // (maybe use stream.exceptions () for this)
> }

Sorry, that's silly. Rather,

unsigned count_lines (std::istream & stream)
{
unsigned count = 0;

enum { max = std::numeric_limits <int>::max };
while (stream.ignore (max, '\n')) ++ count;
return count; // TODO ...
}

Kevin Goodsell

unread,
Mar 24, 2004, 11:08:37 PM3/24/04
to
Buster wrote:

> Buster wrote:
>
>> OK, but you could use getline from the <string> header. Also I'd put
>> this in a separate function:
>>
>> unsigned count_lines (std::istream & stream)
>> {
>> unsigned count = 0;
>> std::string line;
>> while (std::getline (stream, line)) ++ count;
>> return count; // TODO: should make sure it was only eof
>> // (maybe use stream.exceptions () for this)
>> }
>
>
> Sorry, that's silly. Rather,
>
> unsigned count_lines (std::istream & stream)
> {
> unsigned count = 0;
> enum { max = std::numeric_limits <int>::max };

Not sure why you'd use an enum instead of a constant... but the actual
value you want here is std::numerical_limits<std::streamsize>::max.
There was a defect in the standard making it inconsistent on this point.

http://anubis.dkuug.dk/jtc1/sc22/wg21/docs/lwg-defects.html#172

> while (stream.ignore (max, '\n')) ++ count;
> return count; // TODO ...
> }

-Kevin
--
My email address is valid, but changes periodically.
To contact me please use the address from a recent posting.

John Harrison

unread,
Mar 25, 2004, 1:53:20 AM3/25/04
to

"ELIE" <e_a...@ece.concordia.ca> wrote in message
news:9%o8c.101058$9p2.2...@weber.videotron.net...

> Hi, The following is a piece of my code, i am having problems opening a
file
> when i have the while loop to count how many lines are there in my file
> already before i write to it. I have noticed that it works when i take off
> that loop, yet when i put it back on, it gives me the error "Error in
> opening file".
>
> Thanks in advance
>
> fstream Publish("client.txt");
>

Add this

if (!Publish)
{
cerr << "Error in opening file" << endl;
exit(1)
}

It only makes sense to output an error opening files message immediately
after opening the file.

> while (Publish.get(next))
> {
> if ( next == '\n' )
> count++;
>
> }
>
> cout << count;
>

Now you've reached the end of the file, and you attempted to read past the
end of the file, which failed and so your while loop ended. All this is
good, but attempting to read past the end of your file puts the stream in an
error state, therefore nothing will work with the file any more until you
clear the error state. Add this

Publish.clear();

This seems to be a common newbie error.

> Publish.seekg(0, ios::end);
>
> if (!Publish)
> {
> cerr << "Error in opening file" << endl;
> exit(1)
> }

Remove the above.

>
> Publish << s->ReceiveLine();
>
> Publish.close();

Probably no need to close, it happens automatically when Publish is
destructued, which looks to be right now.

>
> }
>

john


Buster

unread,
Mar 25, 2004, 5:41:01 AM3/25/04
to
Kevin Goodsell wrote:

> Buster wrote:
>
>> Sorry, that's silly. Rather,
>>
>> unsigned count_lines (std::istream & stream)
>> {
>> unsigned count = 0;
>> enum { max = std::numeric_limits <int>::max };
>
>
> Not sure why you'd use an enum instead of a constant... but the actual
> value you want here is std::numerical_limits<std::streamsize>::max.

I wrote streamsize first, then thought I ought to look it up in the
standard. Oh well. In any case we're both wrong, because max is a
(static) function. This also means the enum has to go, I think.

0 new messages