2010-11-11 14 views
10

Ceteris paribus (dati ben formati, buone pratiche di buffering e cosa no), c'è un motivo per cui preferisco effettuare il ciclo mentre il ritorno di scanf è 1, anziché !EOF? Potrei aver letto questo da qualche parte, o qualsiasi altra cosa, ma potrei aver sbagliato anch'io. che cosa pensano le altre persone?Mentre scanf! = EOF o scanf == 1?

+3

+1 per impressionante introduzione latina –

+0

Abbastanza simile: http://stackoverflow.com/questions/2970880/using-scanf-in-a-while-loop –

+0

@Steve: heh. L'Academia ti fa questo ... mai notato, e un bel tocco in corsivo ... tu ovviamente vieni anche dal mondo accademico. :) –

risposta

13

scanf restituisce il numero di elementi convertiti con successo ... o EOF in caso di errore. Quindi codifica la condizione nel modo in cui ha senso.

scanfresult = scanf(...); 
while (scanfresult != EOF) /* while scanf didn't error */ 
while (scanfresult == 1) /* while scanf performed 1 assignment */ 
while (scanfresult > 2) /* while scanf performed 3 or more assignments */ 

esempio inventato

scanfresult = scanf("%d", &a); 
/* type "forty two" */ 
if (scanfresult != EOF) /* not scanf error; runs, but `a` hasn't been assigned */; 
if (scanfresult != 1) /* `a` hasn't been assigned */; 

Edit: aggiunto un altro esempio più artificioso

int a[5], b[5]; 
printf("Enter up to 5 pairs of numbers\n"); 
scanfresult = scanf("%d%d%d%d%d%d%d%d%d%d", a+0,b+0,a+1,b+1,a+2,b+2,a+3,b+3,a+4,b+4); 
switch (scanfresult) { 
case EOF: assert(0 && "this didn't happen"); break; 
case 1: case 3: case 5: case 7: case 9: 
    printf("I said **pairs of numbers**\n"); 
    break; 
case 0: 
    printf("What am I supposed to do with no numbers?\n"); 
    break; 
default: 
    pairs = scanfresult/2; 
    dealwithpairs(a, b, pairs); 
    break; 
} 
+0

Questo è solido. Grazie. –

+0

+1 per un buon esempio di codice –

1

Dipende da cosa si vuole fare con ingresso malformati - se il vostro modello isn di scansione Corrispondenza, è possibile ottenere 0 restituito. Quindi, se gestisci il caso al di fuori del ciclo (ad esempio se lo tratti come un errore di input), confronta con 1 (o comunque molti elementi ci sono nella tua chiamata scanf).

0

Da http://www.cplusplus.com/reference/clibrary/cstdio/scanf/

In caso di successo, la funzione restituisce il numero di elementi successo leggere. Questo conteggio può corrispondere al numero previsto di letture o meno, anche a zero, se si verifica un errore di corrispondenza . Nel caso di un errore di input prima che qualsiasi dato possa essere letto correttamente, EOF è restituito.

L'unico modo per essere sicuri di aver letto il numero di elementi previsti è quello di confrontare il valore restituito con quel numero.

+0

Il testo citato non è corretto. Gli elementi letti (ma non memorizzati) utilizzando formati come '% * d' sono ** non conteggiati ** nel valore di ritorno. www.cplusplus.com non sembra essere una buona fonte per informazioni accurate sulla libreria standard C. Se desideri un riferimento online a cui puoi collegarti, POSIX è autorevole; per le funzioni C standard con estensioni POSIX, ha le parti di estensione contrassegnate nei blocchi "CX". Vedi http://www.opengroup.org/onlinepubs/9699919799/functions/scanf.html –