Answer: Every runtime environment must provide three streams viz. standard input, standard output and standard error to every C program. These streams are stdin, stdout and stderr and these are pointers to FILE structure. stdin is default to read from a device which is mostly a keyboard, stdout writes default to a output device which is mostly a terminal or user screen. stderr writes error messages default to terminal or user screen. perror() function writes its error messages to a place where stderr writes its own.
A C program which communicates interactively uses these default streams to perform input and/or output to default devices. For ex.
#include <stdio.h> int main(void) { char *str; printf("how are you, dear xyz?\n"); gets(str); return 0; }
Above program asks the user, “how are you, dear xyz?” and reads in user’s response.
Notice that these default streams are always opened and program has not to bother to open or close them.
While on the other side, reading from and writing to files in a C program requires to take a series of steps,
1. Declare a pointer of type FILE * for each file to be active at the same time. This pointer points to a FILE structure. Then call fopen(), passing it file to be opened and the mode, whether reading, or writing or both to open a stream. fopen() returns a pointer to FILE structure. Every stream has a FILE structure associated with it. This pointer can be used to access its associated stream. fopen() and operating system may verify whether the given file exists, and on some implementations, operating system may check if you have required permissions for accessing the file in the way you have specified and initializes the FILE structure.
2. Next step is to use the FILE structure to perform I/O from and to the files.
3. After you are done with the file I/O, call the fclose() function, passing it FILE structure associated with a given stream to close the stream and releasing the file pointer for use by other stream when needed. Closing the stream prevents you from accessing the associated file again and guarantees that stream buffer is flushed to the file. Let’s take a simple C program to see difference,
/* * fopen_fclose.c -- program attempts to open, process and * close files one by one */ #include <stdio.h> #include <stdlib.h> int main(int argc, char *argv[]) { int exit_status = EXIT_SUCCESS; FILE *fp; int ch; printf("**Program reads in file names as command-line arguments,\n" "attempts to open stream associated with each file in read " "mode\nthen reads from each file one-by-one, before closing" " each.**\n"); while (*++argv != NULL) { /* open files */ fp = fopen(*argv, "r"); /* test if fopen succedded */ if (fp == NULL) { /* give user error massage */ printf("No such %s file", *argv); /* not to exit, instead process another */ /*file name if there's any */ exit_status = EXIT_FAILURE; continue; } /* here we process file */ /* read the contents of the file line by line */ while ((ch = fgetc(fp)) != EOF) { putchar(ch); } putchar('\n'); /* Now we close the stream by passing fp to fclose() */ /* also test if fclose did not fail */ if (fclose(fp) != 0) { perror("fclose(): *argv"); exit(EXIT_FAILURE); } } }
Notice that file names are passed to the program on command-line. Program attempts to open a stream in read mode, one-by-one, for each file, then reads from file and closes the file until a null string is reached. In the event of when a file name doesn’t exist program doesn’t abort. Instead it continues to open the other file if there’s any.
Notice that functions like printf(), putchar(), perror() write to the standard output, while fgetc() reads from the file not from the standard input.
Sanfoundry Global Education & Learning Series – 1000 C Tutorials.
- Check Computer Science Books
- Check C Books
- Watch Advanced C Programming Videos
- Practice BCA MCQs
- Apply for Computer Science Internship