Struct System.Char

Questo articolo fornisce osservazioni supplementari alla documentazione di riferimento per questa API.

La Char struttura rappresenta i punti di codice Unicode usando la codifica UTF-16. Il valore di un Char oggetto è il valore numerico a 16 bit (ordinale).

Se non si ha familiarità con Unicode, valori scalari, punti di codice, coppie di surrogati, UTF-16 e tipo Rune , vedere Introduzione alla codifica dei caratteri in .NET.

Questo articolo esamina la relazione tra un Char oggetto e un carattere e illustra alcune attività comuni eseguite con Char le istanze. È consigliabile considerare il Rune tipo, introdotto in .NET Core 3.0, come alternativa all'esecuzione Char di alcune di queste attività.

Oggetti Char, caratteri Unicode e stringhe

Un String oggetto è una raccolta sequenziale di Char strutture che rappresenta una stringa di testo. La maggior parte dei caratteri Unicode può essere rappresentata da un singolo Char oggetto, ma un carattere codificato come carattere di base, coppia di surrogati e/o sequenza di caratteri combinati è rappresentato da più Char oggetti. Per questo motivo, una Char struttura in un String oggetto non è necessariamente equivalente a un singolo carattere Unicode.

Più unità di codice a 16 bit vengono usate per rappresentare singoli caratteri Unicode nei casi seguenti:

  • Glifi, che possono essere costituiti da un singolo carattere o da un carattere di base seguito da uno o più caratteri combinati. Ad esempio, il carattere ä è rappresentato da un Char oggetto la cui unità di codice è U+0061 seguita da un Char oggetto la cui unità di codice è U+0308. Il carattere ä può anche essere definito da un singolo Char oggetto con un'unità di codice U+00E4. Nell'esempio seguente viene illustrato che il carattere ä è costituito da due Char oggetti.

    using System;
    using System.IO;
    
    public class Example1
    {
        public static void Main()
        {
            StreamWriter sw = new StreamWriter("chars1.txt");
            char[] chars = { '\u0061', '\u0308' };
            string strng = new String(chars);
            sw.WriteLine(strng);
            sw.Close();
        }
    }
    // The example produces the following output:
    //       ä
    
    open System
    open System.IO
    
    let sw = new StreamWriter("chars1.txt")
    let chars = [| '\u0061'; '\u0308' |]
    let string = String chars
    sw.WriteLine string
    sw.Close()
    
    // The example produces the following output:
    //       ä
    
    Imports System.IO
    
    Module Example2
        Public Sub Main()
            Dim sw As New StreamWriter("chars1.txt")
            Dim chars() As Char = {ChrW(&H61), ChrW(&H308)}
            Dim strng As New String(chars)
            sw.WriteLine(strng)
            sw.Close()
        End Sub
    End Module
    ' The example produces the following output:
    '       ä
    
  • Caratteri esterni al piano multilingue Di base Unicode (BMP). Unicode supporta sedici piani oltre al BMP, che rappresenta il piano 0. Un punto di codice Unicode è rappresentato in UTF-32 da un valore a 21 bit che include il piano. Ad esempio, U+1D160 rappresenta il carattere MUSICAL SYMBOL OTTAVO NOTA. Poiché la codifica UTF-16 ha solo 16 bit, i caratteri esterni al BMP sono rappresentati da coppie di surrogati in UTF-16. L'esempio seguente illustra che l'equivalente UTF-32 di U+1D160, il carattere MUSICAL SYMBOL EIGHTH NOTE, è U+D834 U+DD60. U+D834 è il surrogato alto; alta gamma di surrogati da U+D800 a U+DBFF. U+DD60 è il surrogato basso; bassa gamma di surrogati da U+DC00 a U+DFFF.

    using System;
    using System.IO;
    
    public class Example3
    {
        public static void Main()
        {
            StreamWriter sw = new StreamWriter(@".\chars2.txt");
            int utf32 = 0x1D160;
            string surrogate = Char.ConvertFromUtf32(utf32);
            sw.WriteLine("U+{0:X6} UTF-32 = {1} ({2}) UTF-16",
                         utf32, surrogate, ShowCodePoints(surrogate));
            sw.Close();
        }
    
        private static string ShowCodePoints(string value)
        {
            string retval = null;
            foreach (var ch in value)
                retval += String.Format("U+{0:X4} ", Convert.ToUInt16(ch));
    
            return retval.Trim();
        }
    }
    // The example produces the following output:
    //       U+01D160 UTF-32 = ð (U+D834 U+DD60) UTF-16
    
    open System
    open System.IO
    
    let showCodePoints (value: char seq) =
        let str =
            value
            |> Seq.map (fun ch -> $"U+{Convert.ToUInt16 ch:X4}")
            |> String.concat ""
        str.Trim()
    
    let sw = new StreamWriter(@".\chars2.txt")
    let utf32 = 0x1D160
    let surrogate = Char.ConvertFromUtf32 utf32
    sw.WriteLine $"U+{utf32:X6} UTF-32 = {surrogate} ({showCodePoints surrogate}) UTF-16"
    sw.Close()
    
    // The example produces the following output:
    //       U+01D160 UTF-32 = ð (U+D834 U+DD60) UTF-16
    
    Imports System.IO
    
    Module Example4
        Public Sub Main()
            Dim sw As New StreamWriter(".\chars2.txt")
            Dim utf32 As Integer = &H1D160
            Dim surrogate As String = Char.ConvertFromUtf32(utf32)
            sw.WriteLine("U+{0:X6} UTF-32 = {1} ({2}) UTF-16",
                       utf32, surrogate, ShowCodePoints(surrogate))
            sw.Close()
        End Sub
    
        Private Function ShowCodePoints(value As String) As String
            Dim retval As String = Nothing
            For Each ch In value
                retval += String.Format("U+{0:X4} ", Convert.ToUInt16(ch))
            Next
            Return retval.Trim()
        End Function
    End Module
    ' The example produces the following output:
    '       U+01D160 UTF-32 = ð (U+D834 U+DD60) UTF-16
    

Caratteri e categorie di caratteri

Ogni carattere Unicode o coppia di surrogati valida appartiene a una categoria Unicode. In .NET le categorie Unicode sono rappresentate dai membri dell'enumerazione UnicodeCategory e includono valori come UnicodeCategory.CurrencySymbol, UnicodeCategory.LowercaseLettere UnicodeCategory.SpaceSeparator, ad esempio.

Per determinare la categoria Unicode di un carattere, chiamare il GetUnicodeCategory metodo . Nell'esempio seguente, ad esempio, viene chiamato per GetUnicodeCategory visualizzare la categoria Unicode di ogni carattere in una stringa. L'esempio funziona correttamente solo se nell'istanza String non sono presenti coppie di surrogati.

using System;
using System.Globalization;

class Example
{
   public static void Main()
   {
      // Define a string with a variety of character categories.
      String s = "The red car drove down the long, narrow, secluded road.";
      // Determine the category of each character.
      foreach (var ch in s)
         Console.WriteLine("'{0}': {1}", ch, Char.GetUnicodeCategory(ch));
   }
}
// The example displays the following output:
//      'T': UppercaseLetter
//      'h': LowercaseLetter
//      'e': LowercaseLetter
//      ' ': SpaceSeparator
//      'r': LowercaseLetter
//      'e': LowercaseLetter
//      'd': LowercaseLetter
//      ' ': SpaceSeparator
//      'c': LowercaseLetter
//      'a': LowercaseLetter
//      'r': LowercaseLetter
//      ' ': SpaceSeparator
//      'd': LowercaseLetter
//      'r': LowercaseLetter
//      'o': LowercaseLetter
//      'v': LowercaseLetter
//      'e': LowercaseLetter
//      ' ': SpaceSeparator
//      'd': LowercaseLetter
//      'o': LowercaseLetter
//      'w': LowercaseLetter
//      'n': LowercaseLetter
//      ' ': SpaceSeparator
//      't': LowercaseLetter
//      'h': LowercaseLetter
//      'e': LowercaseLetter
//      ' ': SpaceSeparator
//      'l': LowercaseLetter
//      'o': LowercaseLetter
//      'n': LowercaseLetter
//      'g': LowercaseLetter
//      ',': OtherPunctuation
//      ' ': SpaceSeparator
//      'n': LowercaseLetter
//      'a': LowercaseLetter
//      'r': LowercaseLetter
//      'r': LowercaseLetter
//      'o': LowercaseLetter
//      'w': LowercaseLetter
//      ',': OtherPunctuation
//      ' ': SpaceSeparator
//      's': LowercaseLetter
//      'e': LowercaseLetter
//      'c': LowercaseLetter
//      'l': LowercaseLetter
//      'u': LowercaseLetter
//      'd': LowercaseLetter
//      'e': LowercaseLetter
//      'd': LowercaseLetter
//      ' ': SpaceSeparator
//      'r': LowercaseLetter
//      'o': LowercaseLetter
//      'a': LowercaseLetter
//      'd': LowercaseLetter
//      '.': OtherPunctuation
open System

// Define a string with a variety of character categories.
let s = "The red car drove down the long, narrow, secluded road."
// Determine the category of each character.
for ch in s do
    printfn $"'{ch}': {Char.GetUnicodeCategory ch}"

// The example displays the following output:
//      'T': UppercaseLetter
//      'h': LowercaseLetter
//      'e': LowercaseLetter
//      ' ': SpaceSeparator
//      'r': LowercaseLetter
//      'e': LowercaseLetter
//      'd': LowercaseLetter
//      ' ': SpaceSeparator
//      'c': LowercaseLetter
//      'a': LowercaseLetter
//      'r': LowercaseLetter
//      ' ': SpaceSeparator
//      'd': LowercaseLetter
//      'r': LowercaseLetter
//      'o': LowercaseLetter
//      'v': LowercaseLetter
//      'e': LowercaseLetter
//      ' ': SpaceSeparator
//      'd': LowercaseLetter
//      'o': LowercaseLetter
//      'w': LowercaseLetter
//      'n': LowercaseLetter
//      ' ': SpaceSeparator
//      't': LowercaseLetter
//      'h': LowercaseLetter
//      'e': LowercaseLetter
//      ' ': SpaceSeparator
//      'l': LowercaseLetter
//      'o': LowercaseLetter
//      'n': LowercaseLetter
//      'g': LowercaseLetter
//      ',': OtherPunctuation
//      ' ': SpaceSeparator
//      'n': LowercaseLetter
//      'a': LowercaseLetter
//      'r': LowercaseLetter
//      'r': LowercaseLetter
//      'o': LowercaseLetter
//      'w': LowercaseLetter
//      ',': OtherPunctuation
//      ' ': SpaceSeparator
//      's': LowercaseLetter
//      'e': LowercaseLetter
//      'c': LowercaseLetter
//      'l': LowercaseLetter
//      'u': LowercaseLetter
//      'd': LowercaseLetter
//      'e': LowercaseLetter
//      'd': LowercaseLetter
//      ' ': SpaceSeparator
//      'r': LowercaseLetter
//      'o': LowercaseLetter
//      'a': LowercaseLetter
//      'd': LowercaseLetter
//      '.': OtherPunctuation
Imports System.Globalization

Module Example1
    Public Sub Main()
        ' Define a string with a variety of character categories.
        Dim s As String = "The car drove down the narrow, secluded road."
        ' Determine the category of each character.
        For Each ch In s
            Console.WriteLine("'{0}': {1}", ch, Char.GetUnicodeCategory(ch))
        Next
    End Sub
End Module
' The example displays the following output:
'       'T': UppercaseLetter
'       'h': LowercaseLetter
'       'e': LowercaseLetter
'       ' ': SpaceSeparator
'       'r': LowercaseLetter
'       'e': LowercaseLetter
'       'd': LowercaseLetter
'       ' ': SpaceSeparator
'       'c': LowercaseLetter
'       'a': LowercaseLetter
'       'r': LowercaseLetter
'       ' ': SpaceSeparator
'       'd': LowercaseLetter
'       'r': LowercaseLetter
'       'o': LowercaseLetter
'       'v': LowercaseLetter
'       'e': LowercaseLetter
'       ' ': SpaceSeparator
'       'd': LowercaseLetter
'       'o': LowercaseLetter
'       'w': LowercaseLetter
'       'n': LowercaseLetter
'       ' ': SpaceSeparator
'       't': LowercaseLetter
'       'h': LowercaseLetter
'       'e': LowercaseLetter
'       ' ': SpaceSeparator
'       'l': LowercaseLetter
'       'o': LowercaseLetter
'       'n': LowercaseLetter
'       'g': LowercaseLetter
'       ',': OtherPunctuation
'       ' ': SpaceSeparator
'       'n': LowercaseLetter
'       'a': LowercaseLetter
'       'r': LowercaseLetter
'       'r': LowercaseLetter
'       'o': LowercaseLetter
'       'w': LowercaseLetter
'       ',': OtherPunctuation
'       ' ': SpaceSeparator
'       's': LowercaseLetter
'       'e': LowercaseLetter
'       'c': LowercaseLetter
'       'l': LowercaseLetter
'       'u': LowercaseLetter
'       'd': LowercaseLetter
'       'e': LowercaseLetter
'       'd': LowercaseLetter
'       ' ': SpaceSeparator
'       'r': LowercaseLetter
'       'o': LowercaseLetter
'       'a': LowercaseLetter
'       'd': LowercaseLetter
'       '.': OtherPunctuation

Internamente, per i caratteri esterni all'intervallo ASCII (da U+0000 a U+00FF), il GetUnicodeCategory metodo dipende dalle categorie Unicode segnalate dalla CharUnicodeInfo classe . A partire da .NET Framework 4.6.2, i caratteri Unicode vengono classificati in base allo standard Unicode versione 8.0.0. Nelle versioni di .NET Framework da .NET Framework 4 a .NET Framework 4.6.1, vengono classificate in base allo standard Unicode versione 6.3.0.

Caratteri ed elementi di testo

Poiché un singolo carattere può essere rappresentato da più Char oggetti, non è sempre significativo lavorare con singoli Char oggetti. L'esempio seguente, ad esempio, converte i punti di codice Unicode che rappresentano i numeri dell'Egeo da zero a 9 in unità di codice con codifica UTF-16. Poiché equivalgono Char erroneamente agli oggetti con caratteri, segnala in modo non accurato che la stringa risultante ha 20 caratteri.

using System;

public class Example5
{
    public static void Main()
    {
        string result = String.Empty;
        for (int ctr = 0x10107; ctr <= 0x10110; ctr++)  // Range of Aegean numbers.
            result += Char.ConvertFromUtf32(ctr);

        Console.WriteLine("The string contains {0} characters.", result.Length);
    }
}
// The example displays the following output:
//     The string contains 20 characters.
open System

let result =
    [ for i in 0x10107..0x10110 do  // Range of Aegean numbers.
        Char.ConvertFromUtf32 i ]
    |> String.concat ""

printfn $"The string contains {result.Length} characters."


// The example displays the following output:
//     The string contains 20 characters.
Module Example5
    Public Sub Main()
        Dim result As String = String.Empty
        For ctr As Integer = &H10107 To &H10110     ' Range of Aegean numbers.
            result += Char.ConvertFromUtf32(ctr)
        Next
        Console.WriteLine("The string contains {0} characters.", result.Length)
    End Sub
End Module
' The example displays the following output:
'     The string contains 20 characters.

È possibile eseguire le operazioni seguenti per evitare il presupposto che un Char oggetto rappresenti un singolo carattere:

  • È possibile usare un String oggetto nella sua interezza anziché usare i singoli caratteri per rappresentare e analizzare il contenuto linguistico.

  • È possibile usare String.EnumerateRunes come illustrato nell'esempio seguente:

    int CountLetters(string s)
    {
        int letterCount = 0;
    
        foreach (Rune rune in s.EnumerateRunes())
        {
            if (Rune.IsLetter(rune))
            { letterCount++; }
        }
    
        return letterCount;
    }
    
    let countLetters (s: string) =
        let mutable letterCount = 0
    
        for rune in s.EnumerateRunes() do
            if Rune.IsLetter rune then
                letterCount <- letterCount + 1
    
        letterCount
    
  • È possibile usare la StringInfo classe per lavorare con elementi di testo anziché con singoli Char oggetti. Nell'esempio seguente viene utilizzato l'oggetto StringInfo per contare il numero di elementi di testo in una stringa costituita dai numeri dell'Mar Egeo da zero a nove. Poiché considera una coppia di surrogati un singolo carattere, segnala correttamente che la stringa contiene dieci caratteri.

    using System;
    using System.Globalization;
    
    public class Example4
    {
        public static void Main()
        {
            string result = String.Empty;
            for (int ctr = 0x10107; ctr <= 0x10110; ctr++)  // Range of Aegean numbers.
                result += Char.ConvertFromUtf32(ctr);
    
            StringInfo si = new StringInfo(result);
            Console.WriteLine("The string contains {0} characters.",
                              si.LengthInTextElements);
        }
    }
    // The example displays the following output:
    //       The string contains 10 characters.
    
    open System
    open System.Globalization
    
    let result =
        [ for i in 0x10107..0x10110 do  // Range of Aegean numbers.
            Char.ConvertFromUtf32 i ]
        |> String.concat ""
    
    
    let si = StringInfo result
    printfn $"The string contains {si.LengthInTextElements} characters."
    
    // The example displays the following output:
    //       The string contains 10 characters.
    
    Imports System.Globalization
    
    Module Example6
        Public Sub Main()
            Dim result As String = String.Empty
            For ctr As Integer = &H10107 To &H10110     ' Range of Aegean numbers.
                result += Char.ConvertFromUtf32(ctr)
            Next
            Dim si As New StringInfo(result)
            Console.WriteLine("The string contains {0} characters.", si.LengthInTextElements)
        End Sub
    End Module
    ' The example displays the following output:
    '       The string contains 10 characters.
    
  • Se una stringa contiene un carattere di base con uno o più caratteri combinati, è possibile chiamare il String.Normalize metodo per convertire la sottostringa in una singola unità di codice con codifica UTF-16. Nell'esempio seguente viene chiamato il String.Normalize metodo per convertire il carattere di base U+0061 (LATIN SMALL LETTER A) e combinare il carattere U+0308 (COMBINAZIONE DIAERESIS) in U+00E4 (ALFABETO LATINO MINUSCOLO A WITH DIAERESIS).

    using System;
    
    public class Example2
    {
        public static void Main()
        {
            string combining = "\u0061\u0308";
            ShowString(combining);
    
            string normalized = combining.Normalize();
            ShowString(normalized);
        }
    
        private static void ShowString(string s)
        {
            Console.Write("Length of string: {0} (", s.Length);
            for (int ctr = 0; ctr < s.Length; ctr++)
            {
                Console.Write("U+{0:X4}", Convert.ToUInt16(s[ctr]));
                if (ctr != s.Length - 1) Console.Write(" ");
            }
            Console.WriteLine(")\n");
        }
    }
    // The example displays the following output:
    //       Length of string: 2 (U+0061 U+0308)
    //
    //       Length of string: 1 (U+00E4)
    
    open System
    
    let showString (s: string) =
        printf $"Length of string: {s.Length} ("
        for i = 0 to s.Length - 1 do
            printf $"U+{Convert.ToUInt16 s[i]:X4}"
            if i <> s.Length - 1 then printf " "
        printfn ")\n"
    
    let combining = "\u0061\u0308"
    showString combining
    
    let normalized = combining.Normalize()
    showString normalized
    
    // The example displays the following output:
    //       Length of string: 2 (U+0061 U+0308)
    //
    //       Length of string: 1 (U+00E4)
    
    Module Example3
        Public Sub Main()
            Dim combining As String = ChrW(&H61) + ChrW(&H308)
            ShowString(combining)
    
            Dim normalized As String = combining.Normalize()
            ShowString(normalized)
        End Sub
    
        Private Sub ShowString(s As String)
            Console.Write("Length of string: {0} (", s.Length)
            For ctr As Integer = 0 To s.Length - 1
                Console.Write("U+{0:X4}", Convert.ToUInt16(s(ctr)))
                If ctr <> s.Length - 1 Then Console.Write(" ")
            Next
            Console.WriteLine(")")
            Console.WriteLine()
        End Sub
    End Module
    ' The example displays the following output:
    '       Length of string: 2 (U+0061 U+0308)
    '       
    '       Length of string: 1 (U+00E4)
    

Operazioni comuni

La Char struttura fornisce metodi per confrontare Char gli oggetti, convertire il valore dell'oggetto corrente Char in un oggetto di un altro tipo e determinare la categoria Unicode di un Char oggetto:

Operazione da eseguire Usare questi System.Char metodi
Confrontare Char gli oggetti CompareTo e Equals
Convertire un punto di codice in una stringa ConvertFromUtf32

Vedere anche il Rune tipo.
Convertire un Char oggetto o una coppia di oggetti surrogati in un punto di Char codice Per un singolo carattere: Convert.ToInt32(Char)

Per una coppia di surrogati o un carattere in una stringa: Char.ConvertToUtf32

Vedere anche il Rune tipo.
Ottenere la categoria Unicode di un carattere GetUnicodeCategory

Vedere anche Rune.GetUnicodeCategory.
Determinare se un carattere si trova in una determinata categoria Unicode, ad esempio cifra, lettera, punteggiatura, carattere di controllo e così via IsControl, , , , IsLetterOrDigitIsLowSurrogateIsSeparatorIsNumberIsLowerIsPunctuation, e IsSurrogatePairIsUpperIsSurrogateIsSymbolIsLetterIsDigitIsHighSurrogateIsWhiteSpace

Vedere anche i metodi corrispondenti sul Rune tipo.
Convertire un Char oggetto che rappresenta un numero in un tipo valore numerico GetNumericValue

Vedere anche Rune.GetNumericValue.
Convertire un carattere in una stringa in un Char oggetto Parse e TryParse
Convertire un Char oggetto in un String oggetto ToString
Modificare il caso di un Char oggetto ToLower, ToLowerInvariant, ToUpper e ToUpperInvariant

Vedere anche i metodi corrispondenti sul Rune tipo.

Valori char e interoperabilità

Quando un tipo gestito Char , rappresentato come unità di codice con codifica Unicode UTF-16, viene passato al codice non gestito, il marshaller di interoperabilità converte il set di caratteri in ANSI per impostazione predefinita. È possibile applicare l'attributo DllImportAttribute alle dichiarazioni platform invoke e all'attributo StructLayoutAttribute a una dichiarazione di interoperabilità COM per controllare quale set di caratteri usa un tipo sottoposto a marshalling Char .