What's the meaning of EOF ?
2011-09-08 21:44
477 查看
The use and meaning of
will help you understand better. Before I go into too much detail about what
A char
A value that exists at the end of a file
A value that could exist in the middle of a file
And now to what it actually is.
macro defined as an
int with a negative value. It is normally returned by functions that perform
read operations to denote either an error or end of input. Due to variable promotion rules (discussed in detail later), it is important to ensure you
use an int to store the return code from these functions, even if the function appears to be returning a char, such as
Here are some code examples that you might use:
char to int Promotion
By definition an int is larger than a char, therefore a negative valued int can never hold the same value as a char. However,
when you compare an int with a char, the char will get promoted to an int to account for the difference in size of the variables.
The value of a promoted char is affected by its sign, and unfortunately, a char can be either signed or unsigned by default, this is compiler dependant.
To understand this better, let's look at the representation of a few numbers in both ints and chars.
The following assumes 2 byte ints (your compiler might use a larger amount). A char uses only 1 byte (this will be the same amount on your compiler). With the exception of the first column,
the values are shown in hexadecimal.
The "char to int promotion" table makes it clear that the sign of a char produces a very different number in the int.
So what does all this mean to me as a programmer?
Well, let's have a look at a revised version of the code shown above, this time incorrectly using a char variable to store the return code from
Now let's assume that within the file we are reading from is a byte with value 0xff.
2 byte ints). To store this value in a char, it must be demoted, and the char value becomes 0xff.
Next, the char c is compared with the int EOF. Promotion rules apply, and c must be promoted to an int. However, in the sample code, the sign of c isn't explicitly declared, so we don't
know if it's signed or unsigned, so the int value could become either 0xff 0xff or 0x00 0xff. Therefore, the code is is not guaranteed to work in the way we require.
The following is a short program to help show the promotion:
Another scenario to consider is where the char is unsigned. In this case, the process of demoting and promoting the returned value from
have the affect of corrupting the
The following code demonstrates this problem.
EOFseems to cause a lot of confusion with some new coders, hopefully this explanation
will help you understand better. Before I go into too much detail about what
EOFis, I'll tell you what it isn't.
EOFis NOT:
A char
A value that exists at the end of a file
A value that could exist in the middle of a file
And now to what it actually is.
EOFis a
macro defined as an
int with a negative value. It is normally returned by functions that perform
read operations to denote either an error or end of input. Due to variable promotion rules (discussed in detail later), it is important to ensure you
use an int to store the return code from these functions, even if the function appears to be returning a char, such as
getchar()or
fgetc().
Here are some code examples that you might use:
int c; while ((c = fgetc(fp)) != EOF) { putchar (c); }
int ch; while ((ch = cin.get()) != EOF) { cout <<(char)ch; }
char to int Promotion
By definition an int is larger than a char, therefore a negative valued int can never hold the same value as a char. However,
when you compare an int with a char, the char will get promoted to an int to account for the difference in size of the variables.
The value of a promoted char is affected by its sign, and unfortunately, a char can be either signed or unsigned by default, this is compiler dependant.
To understand this better, let's look at the representation of a few numbers in both ints and chars.
The following assumes 2 byte ints (your compiler might use a larger amount). A char uses only 1 byte (this will be the same amount on your compiler). With the exception of the first column,
the values are shown in hexadecimal.
----------------------------- ------------------------------ | char and int comparison | | char to int promotion | ----------------------------- ------------------------------ | Decimal | int | char | | char | unsigned | signed | |---------|---------|-------| |-------|----------|---------| | 2 | 00 02 | 02 | | 02 | 00 02 | 00 02 | | 1 | 00 01 | 01 | | 01 | 00 01 | 00 01 | | 0 | 00 00 | 00 | | 00 | 00 00 | 00 00 | | -1 | FF FF | FF | | FF | 00 FF | FF FF | | -2 | FF FE | FE | | FE | 00 FE | FF FE | ----------------------------- ------------------------------
The "char to int promotion" table makes it clear that the sign of a char produces a very different number in the int.
So what does all this mean to me as a programmer?
Well, let's have a look at a revised version of the code shown above, this time incorrectly using a char variable to store the return code from
fgetc().
char c; while ((c = fgetc(fp)) != EOF) { putchar (c); }
Now let's assume that within the file we are reading from is a byte with value 0xff.
fgetc()returns this value within an int, so it looks like this: 0x00 0xff (again, I'm assuming
2 byte ints). To store this value in a char, it must be demoted, and the char value becomes 0xff.
Next, the char c is compared with the int EOF. Promotion rules apply, and c must be promoted to an int. However, in the sample code, the sign of c isn't explicitly declared, so we don't
know if it's signed or unsigned, so the int value could become either 0xff 0xff or 0x00 0xff. Therefore, the code is is not guaranteed to work in the way we require.
The following is a short program to help show the promotion:
#include <stdio.h> int main(void) { int i = -1; signed char sc = 0xff; unsigned char usc = 0xff; printf ("Comparing %x with %x\n", i, sc); if (i == sc) puts("i == sc"); else puts("i != sc"); putchar ('\n'); printf ("Comparing %x with %x\n", i, usc); if (i == usc) puts("i == usc"); else puts("i != usc"); return 0; } /* * Output Comparing ffff with ffff <--- Notice this has been promoted i == sc Comparing ffff with ff i != usc * */
Another scenario to consider is where the char is unsigned. In this case, the process of demoting and promoting the returned value from
fgetc()will
have the affect of corrupting the
EOFvalue, and the program will get stuck in a infinite loop. Let's follow that process through:
- EOF (0xff 0xff) is returned by fgetc() due to end of input - Value demoted to 0xff to be stored in unsigned char c - unsigned char c promoted to an int, value goes from 0xff to 0x00 0xff - EOF is compared with c, meaning comparison is between 0xff 0xff and 0x00 0xff. - The result is FALSE (the values are different), which is undesirable. - fgetc() is called again, and still returns EOF. The endless loop begins.
The following code demonstrates this problem.
#include <stdio.h> int main(void) { FILE *fp; unsigned char c; if ((fp = fopen("myfile.txt", "rb")) == NULL) { perror ("myfile.txt"); return 0; } while ((c = fgetc(fp)) != EOF) { putchar (c); } fclose(fp); return 0; }
相关文章推荐
- [zt] What do 'statically linked' and 'dynamically linked' mean?
- 关于cat >file,cat <file <<EOF
- unexpected EOF while looking for matching ``'
- What is Mapreduce?&&What is hadoop?
- what's c++
- what href="#" mean?
- What's new in BCGControlBar Library 9.56
- What's the CRUD?
- What's bochs?
- robbin的自白:You've got to find what you love
- WHAT'S NEW IN DELPHI 6
- What's New in System.Xml for Visual Studio 2005 and the .NET Framework 2.0 Release
- What's FreeMarker
- What does => and () => mean in Scala
- what's new in vc2015
- 99. Come what may, heaven won't fall. 做你的吧,天塌不下来
- What is the difference between angle bracket < > and double quotes " " while including header files
- cat >test<<EOF,more