Aakash
Aakash

Reputation: 17

C Language: How to know when there is no more input from stdin when redirecting input from a file

My program is supposed to run in the following way:

CProgram < file.txt

file.txt can has as many rows of data as it wants. For instance,

2 3 G 5 6
5 6 7 
6 9 3 6 H
<<Blank line>>

Is there a way to know that that there is no more input rows? Every file has a blank line at the end.

I am able to read the rows but my program never comes to know if there is no more data to be read and keeps waiting for more data as it would normally expect from stdin.

This is how I am reading it

 while( fgets(line, sizeof(line), stdin) != NULL) {
   ... do something
}

Upvotes: 0

Views: 1067

Answers (3)

paxdiablo
paxdiablo

Reputation: 881523

All of the input functions will give you an end of file indication when the file is finished. For example:

#include <stdio.h>

int main(void) {
    int count = 0;
    while (getchar() != EOF)
        ++count;
    printf("There were %d characters.\n", count);
    return 0;
}

will count the characters in the input stream:

pax> ./testprog <testprog.c
There were 169 characters.

pax> echo -n hello | ./testprog
There were 5 characters.

If you're using fgets (as seems clear from your update), that also allows easy detection:

#include <stdio.h>

static char buff[1000];

int main(void) {
    int count = 0;
    while (fgets(buff, sizeof(buff), stdin) != NULL)
        ++count;
    printf("There were %d lines.\n", count);
    return 0;
}

Running that will count the lines:

pax> ./testprog <testprog.c
There were 12 lines.

You can see in both cases that the end of file is detected correctly using the input redirection or pipe methods. If you're running your code reading from the terminal, you just have to indicate end of file using the facilities your environment provides.

That's usually CTRL-D at the start of the line in UNIX-like operating systems, or CTRL-Z at the start of the line for Windows:

pax> ./testprog
this has
two lines
<Ctrl-D pressed (I run Linux)>
There were 2 lines.

Upvotes: 4

user5550963
user5550963

Reputation:

EOF represents the end of file, so you can read file till you hit EOF

int c = 0;
while ((c = getchar ()) != EOF) { ... }

EDIT:

while ( fgets(line, sizeof(line), stdin) != NULL ) {
    ... do something
}

should work fine since fgets() returns NULL if it hits end of file. At least in Unix like OS (Unix/Linux/BSD/Mac OS) everything is a file, so is standard input. So you can check for EOF on standard input.

Upvotes: 3

Achal
Achal

Reputation: 11921

Since you are reading from stdin and using fgets() , to terminate the loop or there is no more rows to take from user, check the return value of fgets() like below.

char *ptr = NULL;
while( (ptr= fgets(line, sizeof(line), stdin)) != NULL) {
    if( *ptr == '\n')
        break;
    else { /* do something */  }
}

At last when you press ENTER key if condition will be true and it terminates.

Upvotes: 0

Related Questions