3

I have this code which reads a file from the first argument to the main and counts the number of integers stored in it.

#include<stdio.h>
#include <sys/wait.h>
#include <stdlib.h>

int array[100000];
int count = 0;
int main(int argc, char* argv[]){
    FILE* file;
    int i;


    file = fopen(argv[1],"r");

    while(!feof(file)){
        fscanf(file, "%d", &array[count]);
        count++;
    }

    for(i=0; i<count; i++){
        printf(" \n a[%d] = %d\n",i,array[i]);
    }
    return 0;
}

The output when I execute this file is

 a[0] = 1

 a[1] = 2

 a[2] = 3

 a[3] = 4

 a[4] = 5

 a[5] = 6

 a[6] = 7

 a[7] = 8

 a[8] = 9

 a[9] = 10

 a[10] = 0

Why is the value of count one greater than expected?

My input file using "./a.out /home/ghost/Desktop/file.txt" is as follows :

1 2 3 4 5 6 7 8 9 10

Iharob Al Asimi
  • 52,653
  • 6
  • 59
  • 97
Vishwas
  • 506
  • 1
  • 5
  • 20
  • 4
    First mistake `while(!feof(file))` that is wrong! You should read the documentation of `fscanf()` and then you would come up with this `while (fscanf(file, "%d", array[count++]) == 1);` Also, absolutetly no need for global variables. – Iharob Al Asimi Jan 12 '16 at 13:41
  • 1
    You would have spotted/avoided this bug, if you bothered to check return value of `fscanf` (something you should *always* do). – hyde Jan 12 '16 at 13:43
  • @iharob Well, `array` is much safer as a global variable than a local variable in the stack, with that size... And using `malloc` in a snippet like this would just distract from the real issue. So using globals makes sense in the context. – hyde Jan 12 '16 at 13:51
  • @hyde I completely disagree. If the array is defined in `main()` it will have the same lifetime as the whole program. – Iharob Al Asimi Jan 12 '16 at 13:53
  • @iharob I wasn't talking about lifetime, I was talking about stack size being limited. Allocating even just that maybe 5% (~400 KB out of typical 8MB) for the lifetime of the program is rather questionable. – hyde Jan 12 '16 at 14:00
  • @hyde Now I see, didn't pay attention to the size of the array. – Iharob Al Asimi Jan 12 '16 at 14:01

1 Answers1

2
while(!feof(file)){
    fscanf(file, "%d", &array[count]);
    count++;
}

Instead of checking for eof, you need to check the returncode of fscanf():

while(fscanf(file, "%d", &array[count]) == 1)
    count++;

But it would be better to build in some safety too, like:

#define NUM_ITEMS 1000

int array[NUM_ITEMS];

int main(int argc, char* argv[]){
{
    FILE* file;
    int i, count = 0;

    file = fopen(argv[1], "r");

    if (!file) {
        printf("Problem with opening file\n");
        return 0; // or some error code
    }

    while(count < NUM_ITEMS && fscanf(file, "%d", &array[count]) == 1)
        count++;

    fclose(file);

    for(i=0; i<count; i++){
        printf("a[%d] = %d\n", i, array[i]);
    }

    return 0;
}
Danny_ds
  • 11,201
  • 1
  • 24
  • 46