serious_black
serious_black

Reputation: 447

calculation of the length of the file doesn't work

#include "stdio.h"
#include "stdlib.h"
int main()
{
    FILE *fp;
    int noOfLines =0;
    char fname[]="Rtl_Prod_Id.txt";
    printf(fname);
    fp=fopen(fname,"r");
    char ch;

    //looping for every line
    do {
        ch=fgetc(fp);
        if (ch=='\n')
            noOfLines++;
    } while(ch!=EOF);

    //line before the last line
    if (ch!='\n'&&noOfLines!=0)
        noOfLines++;
    fclose(fp);
    printf("%d",noOfLines);
    return 0;
}

I am just trying to calculate the number of lines in my file . The Same doesn't not return me any result .

What are the possible mistakes which i am doing

Environment : AIX and Compiler : CC

Thanks

Edit : My program compiles succesfully but while execute the .Out file it doesn't turn up anything

P.S : Although i got the answer . thanks to https://stackoverflow.com/users/434551/r-sahu . I had change char ch; to int ch; . but i wonder why ? What is wrong in char declaration ? . As i going to check for '\n' and EOF characters why integer then ?

Upvotes: 4

Views: 117

Answers (4)

Ja͢ck
Ja͢ck

Reputation: 173652

The problem is that char on AIX is actually unsigned char.

fgetc() returns an int value and -1 is (typically) used to signal EOF. However, because unsigned char cannot be negative (EOF becomes 255), so the comparison ch != EOF will always be true and this causes an endless loop.

Defining int ch; fixes the problem; btw, this should have shown up during compilation if you use -Wall (show all compiler warnings).

Upvotes: 4

Lee Duhem
Lee Duhem

Reputation: 15121

  1. You should use <...> instead of "..." to include system header files such as stdio.h or stdlib.h.

  2. You should check the return value of fopen for possible error.

  3. The return type of fgetc() is int, not char.

  4. There is a logical flaw in your last line adaption. After the before do {} while loop, ch is EOF, it never will be '\n'. You need another flag to remember if there is any characters after the last '\n', and set it properly in your do {} while loop.

Here is a fixed version of your code, a little more flexible:

#include <stdio.h>
#include <stdlib.h>

int main(int argc, char *argv[])
{
    FILE *fp;
    int noOfLines, isRem, ch;

    if (argc > 1) {
        fp = fopen(argv[1],"r");
        if (fp == NULL) {
            perror("fopen");
            exit(EXIT_FAILURE);
        }
    }
    else {
        fp = stdin;
    }

    noOfLines = 0;
    isRem = 0;

    //looping for every line
    do {
        ch = fgetc(fp);
        if (ch != EOF)
            isRem = 1;
        if (ch == '\n') {
            noOfLines++;
            isRem = 0;
        }
    } while (ch != EOF);

    //line before the last line
    if (isRem)
        noOfLines++;

    if (argc > 1)
        fclose(fp);

    printf("%d\n", noOfLines);

    exit(EXIT_SUCCESS);
}

Testing:

$ wc -l t000.c 
44 t000.c
$ ./a.out t000.c 
44
$ echo -e "abc\ndef" | ./a.out 
2
$ echo -ne "abc\ndef" | ./a.out 
2

Upvotes: 1

Barath Ravikumar
Barath Ravikumar

Reputation: 5836

I had change char ch; to int ch; . but i wonder why ? What is wrong in char declaration ? . As i going to check for '\n' and EOF characters why integer then ?

EOF has a value of -1, and is of type INT, hence ch must be of type INT too.

Also, the prototype of getchar() is

int getchar(void);

so the return of getchar() must always be checked with an integer type.

There is an inherent confusion of EOF, read more about it here

Upvotes: 0

R Sahu
R Sahu

Reputation: 206717

This is a wild shot but changing the line

char ch;

to

int ch;

is appropriate. The return type of fgetc is int, not char.

Upvotes: 1

Related Questions