Prima di andare oltre, dovrei ricordare che ciò che state facendo non è conforme a c/C++. Lo specification afferma in 2.2 quali set di caratteri sono validi nel codice sorgente. Non è molto in là, e tutti i personaggi usati sono in ascii. Quindi ... Tutto quanto segue riguarda un'implementazione specifica (come succede, VC2008 su un computer locale statunitense).
Per iniziare, hai 4 caratteri sulla riga cout
e 4 glifi sull'output. Quindi il problema non è quello della codifica UTF8, poiché combinerebbe più caratteri di origine con meno glifi.
Da te stringa di origine per la visualizzazione sulla console, tutte quelle cose giocano una parte:
- Qual codifica il file sorgente è in (vale a dire come il file C++ sarà visto dal compilatore)
- che il compilatore fa con una stringa letterale, e quale fonte codifica capisce
- come il vostro
<<
interpreta la stringa codificata che stai passando
- quello che codifica per la consolle si aspetta
- come la console traduce quell'output in un glifo font.
Ora ...
1 e 2 sono abbastanza facili. Sembra che il compilatore indovini in che formato si trova il file sorgente e lo decodifica nella sua rappresentazione interna. Genera il segmento di dati corrispondente letterale della stringa nella codepage corrente indipendentemente dalla codifica sorgente. Non sono riuscito a trovare dettagli/controlli espliciti su questo.
3 è ancora più semplice. Ad eccezione dei codici di controllo, <<
passa semplicemente i dati in basso per char *.
4 è controllato da SetConsoleOutputCP
. Dovrebbe essere l'impostazione predefinita per la codepage predefinita del sistema. Puoi anche scoprire quale hai con GetConsoleOutputCP
(l'input è controllato in modo diverso, tramite SetConsoleCP
)
5 è divertente. Ho sbattuto la testa per capire perché non riuscivo a far apparire correttamente l'é, usando CP1252 (Europa occidentale, finestre). Si scopre che il mio font di sistema non ha il glifo per quel personaggio, e usa utilmente il glifo della mia codepage standard (capitale Theta, lo stesso che otterrei se non chiamassi SetConsoleOutputCP). Per risolverlo, ho dovuto cambiare il font che uso sulle console in Lucida Console (un font di tipo true).
Alcune cose interessanti che ho imparato a guardare questo:
- la codifica della fonte non importa, fintanto che il compilatore può capirlo (in particolare, cambiandolo in UTF8 non modificare il codice generato La mia stringa "é" era ancora codificata con CP1252 come
233 0
)
- VC sta selezionando una codepage per i letterali stringa che non sembra controllare.
- controllano ciò che gli spettacoli console è più doloroso di quello che mi aspettavo
Quindi ... che cosa significa questo per voi? Ecco alcuni consigli:
- non utilizzare non-ascii in stringhe letterali. Utilizzare le risorse, dove è controllare la codifica.
- assicurati di sapere quale codifica è prevista dalla tua console e che il tuo font ha i glifi per rappresentare i caratteri che invii.
- se si desidera capire quale codifica viene utilizzata nel proprio caso, si consiglia di stampare il valore effettivo del carattere come numero intero.
char * a = "é"; std::cout << (unsigned int) (unsigned char) a[0]
mostra per me 233, che risulta essere la codifica in CP1252.
A proposito, se quel che abbiamo ottenuto è stato "Ouu" piuttosto che ciò che è stato incollato, allora sembra che il tuo 4 byte sono interpretati da qualche parte come CP850.
Potete darci un po 'più di input. Sta succedendo per l'output di build, tutto l'output o qualcos'altro? Puoi darci una specifica operazione per la quale ciò accade (compilazione, debugging, ecc ...) – JaredPar
Sì, per favore mostra un esempio di ciò che pensi dovrebbe apparire e ciò che effettivamente appare. – wallyk
Cosa succede se usi wcout? – Naveen