Stop reading when reading mutliple files (without goto)

I have files with one column full of numbers, and I want to sum all the files. The problem is being able to exit as soon as invalid data is found (as soon as fprintfit fails).

The first attempt to use goto(and inspired by this answer ) is as follows

while(1) {
    sum_a = 0;
    for(i=0 ; i<N ;i++){
        if(fscanf(infiles[i], "%d\n", &a) != 1){
            goto end; // yeah, I know...
        }
        sum_a += a;
    }
    printf("%d\n", sum_a); // Should NOT be read if anything failed before
}

end:
for(i=0 ; i<N ;i++)
    fclose(infiles[i]);

I would be glad to see a more pleasant solution (i.e. without using gotoand while(1)!). I do not want to ruin a lot of flags set and dropped in a dirty way.

+4
source share
5 answers

Why?

goto. . ?

+7

, goto , : , , :

int stop = 0;
while(!stop) {
    sum_a = 0;
    for(i=0 ; i<N ;i++){
        if(fscanf(infiles[i], "%d\n", &a) != 1){
            stop = 1;
            break;
        }
        sum_a += a;
    }
    if (!stop) {
        printf("%d\n", sum_a);
    }
}
for(i=0 ; i<N ;i++)
    fclose(infiles[i]);

, , printf .

break . :

int i = 0;
for (;;) { // This "forever" loop is idiomatic in C
    if(fscanf(infiles[i], "%d\n", &a) != 1) {
        break;
    }
    sum_a += a;
    if (++i == N) {
        printf("%d\n", sum_a);
        i = 0;
    }
}
for(i=0 ; i<N ;i++)
    fclose(infiles[i]);
+4

:

int rc = 1;
do
{
    sum_a = 0;
    for(i=0 ; i<N ;i++){
        rc = fscanf(infiles[i], "%d\n", &a);
        if(rc == 1){
            sum_a += a;    
            printf("%d\n", sum_a);
        }        
    }
}while(rc == 1);

for(i=0 ; i<N ;i++)
    fclose(infiles[i]);
+2

( ), :

sum_a = 0;
i =0;
while(1) {
        if(fscanf(infiles[i], "%d\n", &a) != 1) break;
        sum_a += a;
        if (++i < N) continue;
        printf("%d\n", sum_a);
        break;
        }

for(i=0 ; i<N ;i++)
    fclose(infiles[i]);

, :

sum_a = 0;
for(i=0 ; i<N ;i++){
    if(fscanf(infiles[i], "%d\n", &a) != 1) break;
    sum_a += a;
    }

if (i == N) printf("%d\n", sum_a);

for(i=0 ; i<N ;i++)
    fclose(infiles[i]);
0

When I need a big exit transition, I usually encapsulate the loops in a function and just use return, for example:

void read(FILE*[] infiles, int N)
{
    for(;;) {
        sum_a = 0;
        for(i=0 ; i<N ;i++){
            if(fscanf(infiles[i], "%d\n", &a) != 1){
                return;
            }
            sum_a += a;
        }
        printf("%d\n", sum_a);
    }
}

void cleanup(FILE*[] infiles, int N)
{
    for(i=0 ; i<N ;i++)
        fclose(infiles[i]);
}

read(infiles, N);
cleanup(infiles, N);

It also helps to read the code.

0
source

All Articles