getc, fgetc, getchar system calls are used to read one character at-a-time.
Definition:
ubuntu@ip-172-31-23-227:~$ less /usr/include/stdio.h
......
/* Read a character from STREAM.
These functions are possible cancellation points and therefore not
marked with __THROW. */
extern int fgetc (FILE *__stream);
extern int getc (FILE *__stream);
/* Read a character from stdin.
This function is a possible cancellation point and therefore not
marked with __THROW. */
extern int getchar (void);
......
The difference between getc and fgetc: getc can be implemented as one macro, fgetc is guaranteed to be a function, calls to fgetc probably takes longer time.
getchar is equal to getc(stdin)
fileio.c:
#include<stdio.h>
#include<stdlib.h>
#include<unistd.h>
int main(int argc, char* argv[])
{
FILE *fp;
if((fp = fopen("test.txt", "r+")) == NULL) {
printf("fopen error!\n");
exit(1);
}
char c1, c2;
c1 = getc(fp);
c2 = fgetc(fp);
printf("c1: %c, c2: %c\n", c1, c2);
printf("input one char: \n");
printf("%c\n", getchar());
fclose(fp);
exit(0);
}
shell:
Run the program, it will read two characters and then instruct the user to input one character, user input 'k', getchar() will catch this char from stdin and output to stdout.
ubuntu@ip-172-31-23-227:~$ ./io.out
c1: a, c2: b
input one char:
k
k
2. Read error
When reading from the stream, both error and encountering the end will return the same negative value. So we need: ferror, feof and clearerr to differentiate the returning information.
definition:
ubuntu@ip-172-31-23-227:~$ less /usr/include/stdio.h
......
/* Clear the error and EOF indicators for STREAM. */
extern void clearerr (FILE *__stream) __THROW;
/* Return the EOF indicator for STREAM. */
extern int feof (FILE *__stream) __THROW __wur;
/* Return the error indicator for STREAM. */
extern int ferror (FILE *__stream) __THROW __wur;
......
fileio.c:
#include<stdio.h>
#include<stdlib.h>
#include<unistd.h>
int main(int argc, char* argv[])
{
FILE *fp;
// Open the file "test.txt" containing only one character 'a'
if((fp = fopen("test.txt", "r+")) == NULL) {
printf("fopen error!\n");
exit(1);
}
// Read 2 characters, 2nd one is EOF
printf("%c ", getc(fp));
printf("%d\n", fgetc(fp));
// run ferror, feof to detect if it is one error or EOF
printf("ferror: %d feof: %d\n", ferror(fp), feof(fp));
if(ferror(fp) > 0) {
printf("error on stream!\n");
} else {
printf("no error!\n");
}
if(feof(fp) > 0) {
printf("reached the end of file\n");
} else {
printf("not reaching the end\n");
}
// Clear up the error flag at FILE struct
clearerr(fp);
printf("After clearerr, ferror: %d, feof: %d\n", ferror(fp), feof(fp));
fclose(fp);
exit(0);
}
shell:
Run the program it will open the "test.txt" containing only one character. It tries to get 2 characters from "test.txt", the first character is "a", the second one is -1, which is EOF, meaning end of file. At this time, FILE's feof flag is turned on. After calling clearerr, all error flags are turned off.
ubuntu@ip-172-31-23-227:~$ ./a.out
a -1
ferror: 0 feof: 1
no error!
reached the end of file
After clearerr, ferror: 0, feof: 0
No comments:
Post a Comment