Domanda

Sto cercando di scrivere un semplice decodificatore UTF-8 per il mio incarico. Sono abbastanza nuovo con C ++ quindi abbi pazienza qui ...

Devo determinare se la codifica è valida o meno, e in entrambi i casi produrre il valore del carattere UTF-8 in esadecimale. Supponiamo di aver letto il primo byte e di aver usato questo primo byte per determinare il numero di byte in questo carattere UTF8. Il problema è che dopo aver letto il primo byte, ho problemi a ripristinare la posizione ifstream di un byte e leggere l'intero carattere UTF-8. Ho provato seekg () e putback (), ma ricevo sempre un errore BUS o un output strano che non sono i miei dati di test. Per favore, grazie.

Anche se posso usare peek () per il primo byte, ma devo ancora leggere i seguenti byte per determinare se la codifica è valida o meno. Il problema di ripristinare la posizione del flusso è ancora presente.

È stato utile?

Soluzione

Suggerirei invece di usare peek () per leggere il primo byte. seekg () dovrebbe funzionare per riavvolgere, ma di solito un errore BUS è causato dal codice che interrompe i problemi di allineamento, il che indica che stai facendo qualcos'altro di male nel tuo codice.

Altri suggerimenti

Perché devi cercare indietro? Non puoi semplicemente leggere il resto della sequenza UTF-8, dopo aver saputo quanti altri ottetti ti aspetti?

Vorrei leggere direttamente il byte successivo e aggiungerlo a quello che ho ricevuto. Come ha detto Ates Goral. È un IMHO più pulito.

Ad ogni modo, puoi spostare il puntatore del flusso usando seekg () :

char byte = 0;
unsigned  int character = 0; // on every usage
ifstream file("test.txt", ios::binary);

file.get(byte);
......
file.seekg(-1, ios::cur); // cur == current position
file.get(
    reinterpret_cast<char*>(&character),
    numberOfBytesAndNullTerminator);

cout << hex << character;

Attenzione che get () nel secondo caso scrive '\ 0' alla fine del carattere . Quindi devi dargli il numero richiesto di byte incluso il terminatore null. Quindi, se vuoi leggere due byte == > numberOfBytesAndNullTerminator = 3 .

Non so perché sia ??necessario ricollocare il personaggio, ma istream :: unget () o istream :: putback () dovrebbero fare quello che vuoi. Cercali nella documentazione del tuo compilatore.

cerca:

ifstream::seekg()
ifstream::teellg()
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top