why won't this work after 158th position? get()

T

tonyjeffs

#include "stdafx.h"
#include "stdafx.h"
#include<iostream>
#include <fstream>

using namespace std;

using std::cout;

int main(int argc, char* argv[])
{
ifstream infile ("b.bmp");
for (int n=0; n<200;n++)
{

int c= infile.get();

if ((n>145)&&(n<165))//print the interesting bit
cout<<c<<" ";
}
return 0;
}

I thought the output would be
23 23 23 0 24 24 24 0 25 25 25 0 26 26 26 0 27 27 27

but it is
23 23 23 0 24 24 24 0 25 25 25 0 -1 -1 -1 -1 -1 -1 -1
b.bmp is a 2k file
from n

Why won't infile.get() work beyond the 157th place?

Thanx
Tony
 
V

Victor Bazarov

#include "stdafx.h"
#include "stdafx.h"

Twice? Please consider weeding out compiler-specific nonsense
when posting there.
#include<iostream>
#include <fstream>

using namespace std;

using std::cout;

Again, twice? You know, 'std::cout' is available as 'cout' after
you wrote 'using namespace std;'...
int main(int argc, char* argv[])

Are you using 'argc' and 'argv'? If not, consider a simpler form
of 'main'.
{
ifstream infile ("b.bmp");
for (int n=0; n<200;n++)
{

int c= infile.get();

What does 'get' get? It gets an int. 'int' is a signed type. Why
are you surprised you get negative numbers?
if ((n>145)&&(n<165))//print the interesting bit
cout<<c<<" ";
}
return 0;
}

I thought the output would be
23 23 23 0 24 24 24 0 25 25 25 0 26 26 26 0 27 27 27

Why did you think that?
but it is
23 23 23 0 24 24 24 0 25 25 25 0 -1 -1 -1 -1 -1 -1 -1
b.bmp is a 2k file
from n

I don't understand. 'b.bmp' is a 2k file. How does that explain what
its contents are?
Why won't infile.get() work beyond the 157th place?

It works just fine. You get some values, don't you?

V
 
P

Peter Jansson

Why won't infile.get() work beyond the 157th place?

What is the size of int on your platform?
156*8=1248 and 156*16=2496 which is approaching the size of your file...
Perhaps you run beyond the end-of-file in your loop so maybe you should
check eof().

Sincerely,
Peter Jansson
http://www.jansson.net/
 
P

Pete Becker

I thought the output would be
23 23 23 0 24 24 24 0 25 25 25 0 26 26 26 0 27 27 27

but it is
23 23 23 0 24 24 24 0 25 25 25 0 -1 -1 -1 -1 -1 -1 -1

Open the file in binary mode. As is, it tries to read control-Z, which
sometimes represents end-of-file, and from then on, returns EOF.
 
G

Greg Schmidt

#include "stdafx.h"
#include "stdafx.h"
#include<iostream>
#include <fstream>

using namespace std;

using std::cout;

int main(int argc, char* argv[])
{
ifstream infile ("b.bmp");
for (int n=0; n<200;n++)
{

int c= infile.get();

if ((n>145)&&(n<165))//print the interesting bit
cout<<c<<" ";
}
return 0;
}

I thought the output would be
23 23 23 0 24 24 24 0 25 25 25 0 26 26 26 0 27 27 27

but it is
23 23 23 0 24 24 24 0 25 25 25 0 -1 -1 -1 -1 -1 -1 -1
b.bmp is a 2k file
from n

Why won't infile.get() work beyond the 157th place?

Thanx
Tony

You are reading the file in text mode, so 26 is interpreted as the EOF
character. Binary files must be opened as binary files, or you will get
this (and potentially other) unexpected behaviour.
 
L

Larry I Smith

#include "stdafx.h"
#include "stdafx.h"

Hmm, this is MS Windows, that has file I/O ramifications...
#include<iostream>
#include <fstream>

using namespace std;

using std::cout;

int main(int argc, char* argv[])
{
ifstream infile ("b.bmp");

In Windows, if "b.bmp" is really a bitmap, then it is a 'binary'
file and must be opened in 'binary' mode to prevent newline
translation and false EOF indicators (i.e. bogus -1 returns by
file reads):

ifstream infile;
infile.open("b.bmp", ios_base::in | ios_base::binary);
for (int n=0; n<200;n++)
{

int c= infile.get();

if ((n>145)&&(n<165))//print the interesting bit
cout<<c<<" ";
}
return 0;
}

I thought the output would be
23 23 23 0 24 24 24 0 25 25 25 0 26 26 26 0 27 27 27

but it is
23 23 23 0 24 24 24 0 25 25 25 0 -1 -1 -1 -1 -1 -1 -1
b.bmp is a 2k file
from n

Why won't infile.get() work beyond the 157th place?

Thanx
Tony

Regards,
Larry
 
L

Larry I Smith

Larry said:
#include "stdafx.h"
#include "stdafx.h"

Hmm, this is MS Windows, that has file I/O ramifications...
#include<iostream>
#include <fstream>

using namespace std;

using std::cout;

int main(int argc, char* argv[])
{
ifstream infile ("b.bmp");

In Windows, if "b.bmp" is really a bitmap, then it is a 'binary'
file and must be opened in 'binary' mode to prevent newline
translation and false EOF indicators (i.e. bogus -1 returns by
file reads):

ifstream infile;
infile.open("b.bmp", ios_base::in | ios_base::binary);

Or you can just do this:

ifstream infile("b.bmp", ios_base::in |
ios_base::binary);
 
P

Pete Becker

Larry said:
In Windows, if "b.bmp" is really a bitmap, then it is a 'binary'
file and must be opened in 'binary' mode to prevent newline
translation and false EOF indicators (i.e. bogus -1 returns by
file reads):

The -1 returns aren't bogus. They're real. Control-Z marks the end of a
file, and having once read that, the eof flag stays set until it's
explicitly cleared.
 
T

tonyjeffs

Thanks.
I think I got it.
Tony

#include<iostream>
#include <fstream>

using namespace std;

int main()
{

ifstream infile ("b.bmp", ifstream::binary);
//binary so it doesn't see 24 as eof
for (int n=0;n<150;n++)
//churn through the first bit without doing anything
infile.get();
for(n=150;n<170;n++)
cout<<infile.get()<<"\n"; //output the results
for(n=170;infile;n++) //runs until infile is false.
{
int d= infile.get(); //I could do something with d!
}

cout<<"\n" "Filesize="<<n<<"\n";

return 0;


}
 
L

Larry I Smith

Pete said:
The -1 returns aren't bogus. They're real. Control-Z marks the end of a
file, and having once read that, the eof flag stays set until it's
explicitly cleared.

This is only true for MS Windows.

They're 'bogus' in the respect that you haven't really
reached the end of the binary file. :)

Larry
 
P

Pete Becker

Larry said:
This is only true for MS Windows.

It's not an OS issue, but an RTL issue. The convention under DOS and
Windows is that ctrl-Z marks the end of a file, so libraries for those
OS's typically treat it as end of file. There may be other systems that
use the same convention. (Probably CP/M did that, too)
They're 'bogus' in the respect that you haven't really
reached the end of the binary file. :)

It's not a binary file if you're reading it as text. The EOF's are
exactly right.
 
L

Larry I Smith

Pete said:
It's not an OS issue, but an RTL issue. The convention under DOS and
Windows is that ctrl-Z marks the end of a file, so libraries for those
OS's typically treat it as end of file. There may be other systems that
use the same convention. (Probably CP/M did that, too)

Yes, I know all of the history...
Modern Windows programs rarely write ctrl-z at the end of a file
anymore.
It's not a binary file if you're reading it as text. The EOF's are
exactly right.

On Windows one reads a binary file in 'text' mode only by mistake;
because doing so produces undefined results (e.g. EOF when the
physical end of file has not actually been reached).

This debate about Windows flaws could go on forever...
So let's NOT continue it.

Regards,
Larry
 
P

Pete Becker

Larry said:
This debate about Windows flaws could go on forever...

I'm not debating Windows flaws. I'm simply discussing how file IO works
in C and C++, which have mechanisms for dealing with the various
conventions for text files that various operating systems adopt.
 
T

tonyjeffs

This's been very helpful. I just realised I never knew what a binary
file was. I always had in the back of my mind the vague thought that
all files are binary since theyre all coded in binary logic.
But now I know :)

cheers

Tony
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,537
Members
45,020
Latest member
GenesisGai

Latest Threads

Top