UTF-8, CString und CFile? (C++, MFC)
Derzeit arbeite ich auf einem MFC-Programm, das speziell arbeiten mit UTF-8. Irgendwann, ich habe das schreiben von UTF-8 Daten in einer Datei; das zu tun, ich bin mit CFiles und CStrings.
Wenn ich Schreibe utf-8 (Russisch Charaktere, um genauer zu sein) Daten in eine Datei, die Ausgabe sieht so aus
Ðàñïå÷àòàíî:
Ñèñòåìà
Ïðîèçâîäñòâî
usw. Dies ist assurely nicht utf-8. Um diese Daten Lesen richtig, ich meine Systemeinstellungen ändern, die nicht-ASCII-Zeichen eines Russischen Codierung Tabelle funktioniert, aber dann sind alle meine Latein-basierten, nicht-ascii-Zeichen bekommen, zu scheitern.
Es ist jedenfalls wie ich es mache.
CFile CSVFile( m_sCible, CFile::modeCreate|CFile::modeWrite);
CString sWorkingLine;
//Add stuff into sWorkingline
CSVFile.Write(sWorkingLine,sWorkingLine.GetLength());
//Clean sWorkingline and start over
Bin ich etwas fehlt? Soll ich stattdessen etwas anderes? Ist es eine Art fangen, die ich verpasst habe?
Ich werde abgestimmt, für Ihre Weisheit und Erfahrung, Kolleginnen und Programmierer.
BEARBEITEN:
Natürlich, als ich nur eine Frage gestellt wird, finde ich schließlich etwas, das interessant sein könnte, gefunden werden kann hier. Dachte, ich könnte es teilen.
EDIT 2:
Okay, also ich habe die Stückliste, um meine Datei, die enthält jetzt chineese Charakter, wahrscheinlich, weil ich nicht konvertieren meiner Zeile auf UTF-8. Fügen Sie die Stückliste habe ich...
char BOM[3]={0xEF, 0xBB, 0xBF};
CSVFile.Write(BOM,3);
Und danach habe ich Hinzugefügt...
TCHAR TestLine;
//Convert the line to UTF-8 multibyte.
WideCharToMultiByte (CP_UTF8,0,sWorkingLine,sWorkingLine.GetLength(),TestLine,strlen(TestLine)+1,NULL,NULL);
//Add the line to file.
CSVFile.Write(TestLine,strlen(TestLine)+1);
Aber dann kann ich nicht kompilieren, da ich nicht wirklich weiß, wie man die Länge der TestLine. strlen scheint nicht zu akzeptieren, TCHAR.
Feste, verwendet eine statische Länge von 1000 statt.
EDIT 3:
So, ich habe diesen code...
wchar_t NewLine[1000];
wcscpy( NewLine, CT2CW( (LPCTSTR) sWorkingLine ));
TCHAR* TCHARBuf = new TCHAR[1000];
//Convert the line to UTF-8 multibyte.
WideCharToMultiByte (CP_UTF8,0,NewLine,1000,TCHARBuf,1000,NULL,NULL);
//Find how many characters we have to add
size_t size = 0;
HRESULT hr = StringCchLength(TCHARBuf, MAX_PATH, &size);
//Add the line to the file
CSVFile.Write(TCHARBuf,size);
Kompiliert er fein, aber wenn ich Blick auf meine neue Datei, es ist genau das gleiche wie wenn ich didn ' T haben alle dieser neuen code (ex : Ðàñïå÷àòàíî:). Es fühlt sich wie ich nicht einen Schritt nach vorne, obwohl ich denke, nur eine kleine Sache ist, was trennt mich vom Sieg.
EDIT 4:
Habe ich entfernt, die Sie zuvor Hinzugefügt code, als Nate Sie gefragt, und ich habe mich entschieden, seinen code statt, was bedeutet, dass jetzt, wenn ich zur Beurteilung meiner Linie, die ich habe...
CT2CA outputString(sWorkingLine, CP_UTF8);
//Add line to file.
CSVFile.Write(outputString,::strlen(outputString));
Alles kompiliert in Ordnung, aber die Russischen Zeichen werden angezeigt ???????. Näher, aber immer noch nicht.
Btw, ich möchte allen danken, die versucht/versucht mir zu helfen, es ist SEHR geschätzt. Ich Hänge schon länger an diesem für eine Weile jetzt, ich kann nicht warten, für dieses problem gegangen zu sein.
FINAL EDIT (hoffe ich)
Durch die änderung der Art habe ich zum ersten mal meine UTF-8-Zeichen (ich neu kodiert, ohne Sie wirklich zu kennen), die fehlerhaft sind, die mit meinem neuen Weg, der die Ausgabe von dem text, ich habe akzeptable Ergebnisse. Indem die UTF-8-BOM char am Anfang meiner Datei, es könnte gelesen werden als Unicode in andere Programme wie Excel.
Hurra! Danke an alle!
InformationsquelleAutor der Frage |
Du musst angemeldet sein, um einen Kommentar abzugeben.
Bei der Ausgabe von Daten, die Sie benötigen, zu tun (dies wird vorausgesetzt, Sie kompilieren im Unicode-Modus, was sehr empfehlenswert ist):
Wenn
_UNICODE
ist nicht definiert (Sie arbeiten in multi-byte-Modus statt), müssen Sie wissen, welche Codepage Sie Ihre Eingabe text und wandelt es in etwas, das Sie verwenden können. Dieses Beispiel zeigt die Arbeit mit dem Russischen text, der im UTF-16-format, speichern Sie es auf UTF-8:Wahrscheinlicher, Ihre russische text ist in einige andere code-Seite, wie KOI-8R. In diesem Fall müssen Sie die Umrechnung von der anderen Codepage in UTF-16. Dann umwandeln von UTF-16 in UTF-8. Sie können nicht konvertieren direkt von KOI-8R UTF-8 mithilfe des conversion-Makros, da Sie immer versuchen zu konvertieren, schmalen text in der system-Codepage. Also der einfache Weg ist, dies zu tun:
Brauchen Sie nicht eine BOM (es ist optional, ich würde es nicht verwenden, es sei denn, es gab einen bestimmten Grund, dies zu tun).
Stellen Sie sicher, Sie Lesen Sie diese: http://msdn.microsoft.com/en-us/library/87zae4a3(VS.80).aspx. Wenn Sie falsch verwenden
CT2CA
(zum Beispiel, indem der Zuweisungs-operator) werden Sie in Schwierigkeiten geraten. Die verlinkten Dokumentation Seite zeigt Beispiele, wie und wie nicht, es zu benutzen.Weitere Informationen:
CT2CA
zeigtconst
. Ich benutze es, wenn möglich, aber einige Konvertierungen unterstützen nur die non-const-version (z.B.CW2A
).CT2CA
zeigt an, dass Sie konvertieren von eineLPCTSTR
. So wird es funktionieren, ob Ihr code wird kompiliert mit der_UNICODE
flag oder nicht. Sie können auchCW2A
(wo W zeigt große Zeichen).CT2CA
zeigt an, dass Sie konvertieren, um ein "ANSI" (8-bit char) string.CT2CA
gibt die Codepage, die Sie konvertieren.Zu tun, die umgekehrte Umwandlung (von UTF-8 zu LPCTSTR), Sie tun können:
In diesem Fall sind wir konvertieren von ein "ANSI" - string in UTF-8-format, zu einem LPCTSTR. Die
LPCTSTR
ist immer davon ausgegangen, dass UTF-16 (wenn_UNICODE
definiert ist) oder die aktuelle Codepage des Systems (wenn_UNICODE
ist nicht definiert).InformationsquelleAutor der Antwort Nate
Müssen Sie konvertieren
sWorkingLine
auf UTF-8 und dann schreiben Sie es in die Datei.WideCharToMultiByte können konvertieren Sie unicode-strings in UTF-8, wenn Sie wählen Sie die
CP_UTF8
codepage.MultiByteToWideChar kann konvertieren ASCII-chars in unicode.
InformationsquelleAutor der Antwort Nick Dandoulakis
Stellen Sie sicher, dass Sie mit Unicode (TCHAR wchar_t). Dann schreiben, bevor Sie die Daten verwenden, konvertieren Sie ihn mithilfe der Win32-API-Funktion WideCharToMultiByte.
InformationsquelleAutor der Antwort user261840