问题
I was trying to understand some basic code and got slightly confused by following code
int main ()
{
FILE *fp;
int c;
int n = 0;
fp = fopen("file.txt","r");
if (fp == NULL)
{
perror("Error in opening file");
return(-1);
}
do
{
c = fgetc(fp);
if ( feof(fp) )
{
break ;
}
printf("%c", c);
} while(1);
fclose(fp);
return(0);
}
Can someone explain me why c is of type integer, even though it is defined by fgetc(fp)
which, from my knowledge, gets just the next character?
回答1:
Given the precise way this particular code has been written, c
wouldn't need to be of type int
--it would still work if c
were of type char
.
Most code that reads characters from a file should (at least initially) read those characters into an int
though. Specifically, part of the basic design of C-style I/O is that functions like getc
and fgetc
can return EOF in addition to any value that could have come from the file. That is to say, any value of type char
could be read from the file. getc
, fgetc
, etc., can signal the end of file by returning at least one value that won't/can't have come from the file. It's usually -1, but that's not guaranteed. When char
is signed (which it usually is, nowadays) you can get a value from the file that will show up as -1 when it's been assigned to a char
, so if you're depending on the return value to detect EOF, this can lead to mis-detection.
The code you've included in the question simply copies the contents of the file to standard output, one character at a time. Making use of the EOF return value, we can simplify the code a little bit, so the main loop looks like this:
int c;
while (EOF != (c = fgetc(fp)))
printf("%c", c); // or: putchar(c);
I suppose some might find this excessively terse. Others may object to the assignment inside the condition of the loop. I, at least, think those are reasonable and valid arguments, but this still fits enough better with the design of the library that it's preferable.
回答2:
The signature of fgetc
int fgetc ( FILE * stream );
And about return value of fgetc
On success, the character read is returned (promoted to an int value). The return type is int to accommodate for the special value
EOF
, which indicates failure.
So we declare variable as integer. As character may be unsigned which can't take negative value. But implementation of EOF
always negative or very commonly -1
which can be use as failure or end of file. So it is safe to use integer and can be use like
int c;
while ((c = fgetc(fp))!=EOF){
//Code goes here
}
来源:https://stackoverflow.com/questions/32640855/integer-variable-used-with-fgetc