2009-03-30 12 views
7

Ist es in C# möglich, UTF-32-Zeichen nicht in Ebene 0 als Zeichen zu verwenden?C# - und UTF-16-Zeichen

string s = ""; // valid 
char c = ''; // generates a compiler error ("Too many characters in character literal") 

Und in s wird es durch zwei Zeichen, nicht eins dargestellt.

Edit: Ich meine, gibt es ein Zeichen AN String-Typ mit voller Unicode-Unterstützung, UTF-32 oder UTF-8 pro Zeichen? Zum Beispiel, wenn ich eine for-Schleife auf utf-32 (vielleicht nicht in Ebene 0) Zeichen in einer Zeichenfolge haben möchte.

Antwort

9

Die Klasse string repräsentiert einen UTF-16-kodierten Textblock, und jeder char in einem string repräsentiert einen UTF-16-Codewert.

Obwohl es kein BCL-Typ ist, die einen einzigen Unicode-Codepunkt darstellt, gibt Unterstützung jenseits Flugzeug für Unicode-Zeichen 0 in Form ein Verfahren Überlastungen string und einen Index, statt nur ein char nehmen. Zum Beispiel hat die statische GetUnicodeCategory(char)-Methode der Klasse System.Globalization.CharUnicodeInfo eine entsprechende GetUnicodeCategory(string,int)-Methode, die ein einfaches Zeichen oder ein Ersatzpaar ab dem angegebenen Index erkennt.


durch die Textelemente in einem string iterieren, können Sie die Methoden auf der System.Globalization.StringInfo Klasse verwenden können. Hier entspricht ein "Textelement" einem einzelnen Zeichen, wie es auf dem Bildschirm angezeigt wird. Dies bedeutet, dass einfache Zeichen ("a"), die Zeichen kombinieren ("a\u0304\u0308" = "a & # x0304; & # x0308;"), und Ersatzpaare ("\uD950\uDF21" = "& # xD950; & # xDF21;") alle als eine Einheit behandelt werden Textelement.

Speziell die statische Methode GetTextElementEnumerator ermöglicht es Ihnen, über jedes Textelement in einer string aufzuzählen (siehe die verknüpfte MSDN-Seite für ein Codebeispiel).

+1

Gute Präsentation der Fakten. Beachten Sie, dass C# Ihnen erlaubt, '" \ U00064321 "' (genau acht hexadezimale Ziffern nach dem '\ U') zu verwenden, was äquivalent zu" \ uD950 \ uDF21 "' ist, aber einfacher von einem Unicode/UTF-32 zu verstehen ist Standpunkt. Dies ist ein Codepunkt in [Ebene 6] (https://en.wikipedia.org/wiki/Plane_ (Unicode) #Unassigned_planes). –

4

Ich kenne nur dieses Problem von Java und überprüfte die documentation on char vor der Beantwortung und in der Tat ist das Verhalten in .NET/C# und Java ziemlich ähnlich.

Es scheint, dass in der Tat ein char 16 Bit sein definiert ist und auf jeden Fall nicht 0 etwas außerhalb von Flugzeug, kann nur String/string ist in der Lage, diese Zeichen zu verarbeiten. In einem char-Array wird es als two surrogate characters dargestellt.

3

C# System.String unterstützt UTF-32 gut, aber Sie können nicht durch die Zeichenfolge wie ein Array von System.Char durchlaufen oder IEnumerable verwenden.

zum Beispiel:

// iterating through a string NO UTF-32 SUPPORT 
for (int i = 0; i < sample.Length; ++i) 
{ 
    if (Char.IsDigit(sample[i])) 
    { 
     Console.WriteLine("IsDigit"); 
    } 
    else if (Char.IsLetter(sample[i])) 
    { 
     Console.WriteLine("IsLetter"); 
    } 
} 

// iterating through a string WITH UTF-32 SUPPORT 
for (int i = 0; i < sample.Length; ++i) 
{ 
    if (Char.IsDigit(sample, i)) 
    { 
     Console.WriteLine("IsDigit"); 
    } 
    else if (Char.IsLetter(sample, i)) 
    { 
     Console.WriteLine("IsLetter"); 
    } 

    if (Char.IsSurrogate(sample, i)) 
    { 
     ++i; 
    } 
} 

Hinweis der feine Unterschied in der Char.IsDigit und Char.IsLetter nennt. Und diese String.Length ist immer die Anzahl der 16-Bit-Zeichen, nicht die Anzahl der Zeichen im UTF-32-Sinn.

Off Topic, aber UTF-32-Unterstützung ist völlig unnötig für eine Anwendung, um internationale Sprachen zu behandeln, es sei denn, Sie haben einen bestimmten Geschäftsfall für eine obskure historische/technische Sprache.

+0

Wovon du sprichst, ist nicht UTF-32, sondern nur UTF-16, das zufällig zusätzliche Zeichen enthält. In UTF-32 wird jedes Zeichen als vier Bytes gespeichert. .NET-Zeichenfolgen sind immer UTF-16. –

+1

Anstelle von "mit UTF-32-Unterstützung" sollte das Beispiel wahrscheinlich "mit Ersatzpaar-Unterstützung" oder "mit Unterstützung für tatsächliche Zeichen, nicht nur 16-Bit-Stücke von I-Hoffnung-this-char-is-in-the" -BMP ". – Triynko