Newsgroup: it.comp.lang.c
Titolo: Problema di lettura da un file bitmap

Ciao,
ho un problema con questa istruzione.
while ( ((ch=fgetc(infile))!=0) && !feof(infile) ) {
...
infile è aperto in modalità "rb" e ch è un int.
Il problema è che con alcuni file, la condizione è falsa.
In particolare, sto usando il file 'pic' del Calgary Corpus,
reperibile a 
ftp://ftp.cpsc.ucalgary.ca/
Si tratta di un'immagine bitmap b/n.
Con questo file, già al primo byte il corpo del ciclo non
viene eseguito.
Non so, forse dipende da feof. Dovrei usare ferror?
Si può prendere per buono che ferror controlla tutti i casi
di errore, compreso l'end of file?
Grazie mille,
@le

infile è aperto in modalità "rb" e ch è un int.
Se il primo byte del file e' '\0' il tuo ciclo
non viene eseguito. Zero e' un valore come un altro...
per leggere tutti i byte devi confrontare con EOF
(che normalmente e' definito -1):
   while ((ch=fgetc(infile))!=EOF)
   {
     ...
   }
Nota e' che molto importante che ch sia dichiarato
int e non char.
HTH
Andrea
--
Andrea Griffini, Programmer
http://www.netservers.com/~agriff

 int e non char.
Perchè? Spiegamelo bene, perfavore. In altri punti del programma
ho usato unsigned char. Qual'è il rischio?
Grazie,
@le

ho usato unsigned char. Qual'č il rischio?
e' importante nei valori letti con fgetc perche' quella
funzione non torna un char ma torna un intero.
Il motivo per cui fgetc e' stata progettata in questo
modo e' che che oltre a tutti i possibili caratteri deve
anche essere in grado di segnalare la condizione di fine
file tornando EOF. Se tu memorizzi il risultato di fgetc
in un char pero' perdi la possibilita' di capire quando
il file finisce (infatti in un carattere ci stanno solo
tutti i possibili caratteri).
E' chiaro che una volta che hai visto che il valore non
e' EOF puoi memorizzare il valore in un unsigned char
senza nessun problema.


 senza nessun problema.
Ed è quindi questo il modo giusto di procedere?
Nel mio caso, il programma legge un byte alla volta.
E' un compressore, e le routine successive sono fatte in modo da
elaborare blocchi di 8 bit. Quindi penso - spero - che fgetc() sia la
scelta più logica. Come dovrei trasformare l'istruzione di lettura?
Così è come hai scritto tu:
...
int ch;
...
while ((ch=fgetc(infile))!=EOF)
...
Non dovrei aggiungere && !feof(infile)  ?
Il libro che ho dice che in modalità binaria si può leggere un intero
uguale a EOF anche se la fine fisica del file non è stata raggiunta, e
di usare feof(). Che ne pensi?
Inoltre, vale la pena di usare ferror()?
Grazie mille,
@le

di usare feof(). Che ne pensi?
che libro e' ? Ho quasi un sospetto...
Comunque fgetc torna EOF sia in caso di fine file che
in caso di errore. Al limite controlla ferror dopo
l'uscita dal ciclo.


 che libro e' ? Ho quasi un sospetto...
So qual'è il tuo sospetto ed è azzeccato: è lo Schildt.
Mi procurerò un altro libro.
Quindi quanto scritto sopra è sbagliato?
E quindi e' impossibile leggere EOF,
se non in caso di errore, prima della fine fisica del file?
THX,
@le

se non in caso di errore, prima della fine fisica del file?
Esatto. Il problema e' bisogna stare attenti a non
memorizzare il risultato di fgetc in un char perche' cosi'
facendo si buttano via dei bit importanti (che permettono
di distinguere EOF da tutti gli altri char).
Se fgetc viene usato correttamente (ovvero memorizzandone
il risultato in un int) allora e' impossibile leggere da
file dei falsi "eof" anche se il file e' aperto in
modalita' binaria: la modalita' binaria ha solo a che fare
con la gestione dei fine linea e su alcuni sistemi col
modo in cui vengono presentati i dati provenienti da file
a record fisso.


 memorizzare il risultato di fgetc in un char [...]
Il problema esiste anche in scrittura? Mi spiego meglio: ho una
variabile unsigned short k. Questa istruzione è corretta? (voglio
che l'output sul file occupi un solo byte)
    fputc((unsigned char)(48+k), outfile);
Grazie,
@le

 >se non in caso di errore, prima della fine fisica del file?
Bisogna distinguere il carattere di EOF che dovrebbe essere quello
con codice ASCII 22 dall'errore EOF (-1) ritornato dalla fgetc().
Il carattere di EOF sta alla fine del file di "testo" se si può fare una
distinzione.
Di solito il carattere di EOF si usa anche per alla fine delle signature nei
file
in modo che se un fa da dos  "type nomefile" o gli esce solo la signature
perchè
type crede che il file finisca dopo il carattere 22....

@less@ndro <nob...@nowhere.invalid> wrote in message
96ujlt$pso$1...@pegasus.tiscalinet.it...
