wide char, mbyte char, Unicode



  • __fricky schrieb:

    L"hello" sollte 12 bytes haben.
    🙂

    ...wegen dem Terminierungszeichen '\0', welches ebenfalls 2Byte groß ist.



  • __fricky schrieb:

    wchar_t muss so gross sein wie ein 'int'

    Nö, woher hast du das?

    ISO C99 schrieb:

    wchar_t
    which is an integer type whose range of values can represent distinct codes for all
    members of the largest extended character set specified among the supported locales;

    __fricky schrieb:

    32 bits sind ja die reinste verschwendung.

    Nein, nach dem Standard ein Muss, wenn das System Unicode 4/5 unterstützt.

    __fricky schrieb:

    L"hello" sollte 12 bytes haben.
    🙂

    Nö, 24 bytes.

    @jsbach

    Was willst du denn genau machen? Für Unicode-Support könnte sich vielleicht eher UTF-8 lohnen. http://en.wikipedia.org/wiki/UTF-8

    http://www.cl.cam.ac.uk/~mgk25/unicode.html#c



  • rüdiger schrieb:

    __fricky schrieb:

    wchar_t muss so gross sein wie ein 'int'

    Nö, woher hast du das?

    ISO C99 schrieb:

    wchar_t
    which is an integer type whose range of values can represent distinct codes for all
    members of the largest extended character set specified among the supported locales;

    ich weiss nicht mehr woher, aber falsch in erinnerung.
    auf windosen jedenfalls (zumindest auf etwas älteren) besteht wchar_t aus 2 bytes.
    🙂



  • __fricky schrieb:

    ich weiss nicht mehr woher, aber falsch in erinnerung.
    auf windosen jedenfalls (zumindest auf etwas älteren) besteht wchar_t aus 2 bytes.
    🙂

    Das ist aber nicht konform mit dem Standard. Das rührt einfach daher, dass für die ersten Unicode-Versionen 2byte genug waren und MS will das aus Gründen der Kompatibilität nicht ändern und benutzt daher UTF-16, was das ganze aber noch mehr broken macht, da das ganze eben nicht auf Multibyte-Zeichensätze ausgelegt ist.



  • rüdiger schrieb:

    Das ist aber nicht konform mit dem Standard. Das rührt einfach daher, dass für die ersten Unicode-Versionen 2byte genug waren und MS will das aus Gründen der Kompatibilität nicht ändern und benutzt daher UTF-16, was das ganze aber noch mehr broken macht, da das ganze eben nicht auf Multibyte-Zeichensätze ausgelegt ist.

    standard hin oder her, windows stammt noch aus der vor-standardzeit und m$ vertickerte windoze damals schon in chinesisch. im windosen kernel sind z.b. alle strings utf-16. alle winapi-funktionen, die zeichenketten entgegennehmen, gibt es in 2-facher ausführung (einmal mit char* und einmal mit wchar_t*). eine änderung auf utf-32 oder utf-8 würde wohl kaum einen gewinn bringen. deshalb lassen sie's so.
    🙂



  • __troll schrieb:

    rüdiger schrieb:

    Das ist aber nicht konform mit dem Standard. Das rührt einfach daher, dass für die ersten Unicode-Versionen 2byte genug waren und MS will das aus Gründen der Kompatibilität nicht ändern und benutzt daher UTF-16, was das ganze aber noch mehr broken macht, da das ganze eben nicht auf Multibyte-Zeichensätze ausgelegt ist.

    standard hin oder her, windows stammt noch aus der vor-standardzeit und m$ vertickerte windoze damals schon in chinesisch. im windosen kernel sind z.b. alle strings utf-16. alle winapi-funktionen, die zeichenketten entgegennehmen, gibt es in 2-facher ausführung (einmal mit char* und einmal mit wchar_t*). eine änderung auf utf-32 oder utf-8 würde wohl kaum einen gewinn bringen. deshalb lassen sie's so.
    🙂

    bla bla bla



  • blablubb schrieb:

    __fricky schrieb:

    rüdiger schrieb:

    Das ist aber nicht konform mit dem Standard. Das rührt einfach daher, dass für die ersten Unicode-Versionen 2byte genug waren und MS will das aus Gründen der Kompatibilität nicht ändern und benutzt daher UTF-16, was das ganze aber noch mehr broken macht, da das ganze eben nicht auf Multibyte-Zeichensätze ausgelegt ist.

    standard hin oder her, windows stammt noch aus der vor-standardzeit und m$ vertickerte windoze damals schon in chinesisch. im windosen kernel sind z.b. alle strings utf-16. alle winapi-funktionen, die zeichenketten entgegennehmen, gibt es in 2-facher ausführung (einmal mit char* und einmal mit wchar_t*). eine änderung auf utf-32 oder utf-8 würde wohl kaum einen gewinn bringen. deshalb lassen sie's so.
    🙂

    bla bla bla

    so ist das halt auf den internet-boards.
    🙂



  • rüdiger schrieb:

    __fricky schrieb:

    wchar_t muss so gross sein wie ein 'int'

    Nein, nach dem Standard ein Muss, wenn das System Unicode 4/5 unterstützt.

    Wie stellt man das fest bei 0S? Gibt's einen Macro dafuer? Wuerde
    ein check von __STDC_ISO_10646__ ausreichen?

    rüdiger schrieb:

    @jsbach

    Was willst du denn genau machen? Für Unicode-Support könnte sich vielleicht eher UTF-8 lohnen. http://en.wikipedia.org/wiki/UTF-8

    http://www.cl.cam.ac.uk/~mgk25/unicode.html#c

    Danke fuer die Links. Das Protokoll, das ich schreibe soll UTF-8 unterstuetzen.
    Dabei moechte ich fuer jeden char einen festen Groesse von Bytes(4) haben anstatt
    multibyte encoding oder decoding. Das waere dann simpler.



  • jsbach schrieb:

    rüdiger schrieb:

    __fricky schrieb:

    wchar_t muss so gross sein wie ein 'int'

    Nein, nach dem Standard ein Muss, wenn das System Unicode 4/5 unterstützt.

    Wie stellt man das fest bei 0S? Gibt's einen Macro dafuer? Wuerde
    ein check von __STDC_ISO_10646__ ausreichen?

    mach doch sizeof(wchar_t). das müsste dann 2,3, oder 4 ausspucken. also je nachdem wie breit es bei dir ist.

    jsbach schrieb:

    Das Protokoll, das ich schreibe soll UTF-8 unterstuetzen.
    Dabei moechte ich fuer jeden char einen festen Groesse von Bytes(4) haben anstatt
    multibyte encoding oder decoding. Das waere dann simpler.

    das wär aber doof, weil der trick bei utf-8 ist ja gerade, dass unicode platzsparend gespeichert oder übertragen wird.
    🙂



  • fricky schrieb:

    jsbach schrieb:

    Das Protokoll, das ich schreibe soll UTF-8 unterstuetzen.
    Dabei moechte ich fuer jeden char einen festen Groesse von Bytes(4) haben anstatt
    multibyte encoding oder decoding. Das waere dann simpler.

    das wär aber doof, weil der trick bei utf-8 ist ja gerade, dass unicode platzsparend gespeichert oder übertragen wird.
    🙂

    Na das Problem ist, ich muss alles in einem byte order rueberschieben.
    Wenn ich den multibyte methode benutzen wuerde, heisst ja dann dass ich
    jeden char nach einem Muster vergleichen muss , damit ich feststellen kann um
    wie viel Bytes es fuer diesen wchar tatsaechlich geht. Erst dann waere ich in
    der Lage swap_bytes() in little_endian auszufuehren.
    Wenn ich aber festen Laenge habe, spare ich mir diesen Mustervergleich.

    Da ich im Bereich Unicode Anfaenger bin, stelle ich ne Frage: Sowie ich von
    Unicode verstanden habe, kann man auch feste Laenge fuer jeden
    Char benutzen. Ist es dann nicht mehr UTF-8 encoding?



  • jsbach schrieb:

    Ist es dann nicht mehr UTF-8 encoding?

    richtig. bei utf-8 haben die zeichen variable längen, während du utf-32 verwenden willst. bei utf-32 belegt jedes zeichen immer 4 bytes.
    🙂



  • meiner meinung nach sind 4 byte pro zeichen zu viel. soweit ich weiß, kann man in allen lebenden sprachen alles ausdrücken, was man will, wenn man 2 byte verwendet. außerdem gibt es kaum schriftarten, die alle buchstaben darstellen würden. sind ja bereits 1,1 millionen.

    utf8 in strings zu verwenden, bringt vermeintlich einen vorteil, wird aber dann bei indiziertem zugriff auf einen buchstaben kompliziert, da man vom start des strings weiterzählen muss, da die buchstaben ja nicht alle gleich lang sind. ein einfaches start + n * index klappt da nicht mehr.



  • besserwisser schrieb:

    meiner meinung nach sind 4 byte pro zeichen zu viel. soweit ich weiß, kann man in allen lebenden sprachen alles ausdrücken, was man will, wenn man 2 byte verwendet. außerdem gibt es kaum schriftarten, die alle buchstaben darstellen würden. sind ja bereits 1,1 millionen.

    utf8 in strings zu verwenden, bringt vermeintlich einen vorteil, wird aber dann bei indiziertem zugriff auf einen buchstaben kompliziert, da man vom start des strings weiterzählen muss, da die buchstaben ja nicht alle gleich lang sind. ein einfaches start + n * index klappt da nicht mehr.

    UTF-8 ist ja auch nicht dafür gemacht, sondern zur effizienten Speicherung.



  • fricky schrieb:

    jsbach schrieb:

    Ist es dann nicht mehr UTF-8 encoding?

    richtig. bei utf-8 haben die zeichen variable längen, während du utf-32 verwenden willst. bei utf-32 belegt jedes zeichen immer 4 bytes.
    🙂

    danke fuer die Erklaerung. Ich habe mich fuer UTF-8 entschieden und
    implementiert.

    Eine andere Sache was mich ueberrascht hat, dass die byte order von unicode
    endianness ist. Also ein multibyte char (von 3 byte Laenge) wird auf x86 in dem
    gleichen byte Reihenfolge gespeichert wie bei sparc. Ich habe mir eigentlich die
    Speicherung umgekehrt -genauso wie standarde datentypen(int, short als2bytes, long)- vorgestellt.



  • Ist doch egal wie, hauptsache einheitlich.



  • Wie macht man aus einem wide char array ein ansi char array?



  • zuhülfe schrieb:

    Wie macht man aus einem wide char array ein ansi char array?

    Meinst du mit Wide-Char wirklich Wide-Char oder doch Multi-Byte?
    Bei einem Wide-Char musst du einfach nur Wide-Char für Wide-Char durchgehen, alles was in ein char passt, größentechnisch, kannst du direkt in char Casten, alles andere kannst du nicht mit ansi darstellen und dafür ein Placeholder einfügen, z.B. ?
    Vorausgesetzt das Wide-Char Array enthält Zeichen in einem Zeichencode der den Ansi-Zeichensatz in die ersten 255 Zahlen mappt.



  • ok, dankeschön. 🙂

    Gibt es denn eine Funktion, die Ansi Strings in wide strings verpackt, oder muss man das selber machen?



  • Ganz einfach schrieb:

    ...alles was in ein char passt, größentechnisch, kannst du direkt in char Casten, alles andere kannst du nicht mit ansi darstellen..

    Ganz so einfach nicht.
    Was du beschreibst ist die ASCII, bei dem nur die Werte 0..127 belegt sind. Da gibt es also auch keine deutschen Umlaute.

    Mit "ANSI Code Pages" werden i.A. unter Windows Code Pages bezeichnet, die die Werte 128..255 mit sprach/regionsspezifischen Zeichen auffüllen. Will man also den Wide Char - string dahin umwandeln, muß man auch die Code Page mit angeben.

    Unter Windows kommt man mit WideCharToMultiByte und MultiByteToWideChar hin und her.

    code pages supported by windows
    mb2wc
    wc2mb

    klugscheißer schrieb:

    UTF-8 ist ja auch nicht dafür gemacht, sondern zur effizienten Speicherung.

    ... und indexbasierter Zugriff klappt auch bei UTF-16 nicht mehr 🙂


Anmelden zum Antworten