Stringhe C#

Tip

Questo articolo fa parte della sezione Nozioni fondamentali per gli sviluppatori che già conoscono almeno un linguaggio di programmazione e stanno imparando C#. Se non si ha familiarità con la programmazione, iniziare prima con le esercitazioni introduttive .

Provenienti da Java o C++? C# string è un tipo riferimento non modificabile supportato da String. UTF-16 è la codifica in memoria, simile a Java String. A differenza di C/C++, le stringhe non vengono terminate con null e non vengono decadite in puntatori.

Una stringa è una sequenza di caratteri. In C# string è la parola chiave del linguaggio per il System.String tipo. Ogni letterale di stringa che scrivi produce un'istanza di System.String.

string e String

La string parola chiave e il nome del String tipo fanno riferimento allo stesso tipo. Vengono compilati in un linguaggio intermedio identico (IL).

// The 'string' keyword is an alias for System.String. The two are identical.
string a = "hello";
String b = "hello";

Console.WriteLine(a == b);                // True
Console.WriteLine(typeof(string) == typeof(String)); // True

Usa la parola chiave string nel tuo codice. È coerente con le altre parole chiave di tipo predefinite (int, bool, double) e funziona senza una using System; direttiva.

Le stringhe non sono modificabili

Non modificabile significa che il valore non può essere modificato dopo la creazione. Dopo aver creato un stringoggetto , non è possibile modificarne i caratteri. Metodi come ToUpperInvariant, ReplaceSubstring, e Trim restituiscono una nuova stringa contenente il valore modificato. L'istanza originale rimane invariata.

string greeting = "hello";

// ToUpper returns a *new* string. The original is unchanged.
string shouted = greeting.ToUpperInvariant();

Console.WriteLine(greeting);  // hello
Console.WriteLine(shouted);   // HELLO

Poiché le stringhe non sono modificabili, è possibile condividerle in modo sicuro tra metodi e thread. Questa immutabilità spiega perché il string tipo si comporta come un tipo valore in uso quotidiano anche se si tratta di un tipo riferimento.

Quando si compila una stringa da molti piccoli pezzi in un ciclo, usare StringBuilder per accodare e produrre una singola stringa alla fine:

// For many sequential edits, StringBuilder avoids allocating a new string each time.
var builder = new StringBuilder();
for (int i = 1; i <= 3; i++)
{
    builder.Append("item ").Append(i).Append(';');
}
string result = builder.ToString();
Console.WriteLine(result);    // item 1;item 2;item 3;

Valori letterali di stringa

C# offre quattro forme letterali. Ogni modulo è adatto a contenuti diversi. Come guida rapida:

  • Usare valori letterali regolari per testo breve e semplice con al massimo alcune sequenze di escape.
  • Usare i letterali verbatim quando nel contenuto prevalgono le barre rovesciate, ad esempio nei percorsi di Windows o nei pattern regex.
  • Usare stringhe letterali raw per testo su più righe o con formattazione strutturata, ad esempio JSON inline, SQL, XML o blocchi di messaggi formattati.
  • Aggiungere un $ prefisso a uno dei valori letterali sopra indicati per ottenere una stringa interpolata quando è necessario incorporare i valori.
  • Aggiungere il suffisso u8 a un letterale per produrre una sequenza di byte UTF-8 (ovvero un ReadOnlySpan<T> di byte) per le API orientate ai byte. Per informazioni dettagliate, vedere Valori letterali stringa UTF-8 nelle informazioni di riferimento sul linguaggio.

Valori letterali regolari e sequenze di escape

Una stringa letterale regolare è racchiusa tra virgolette doppie. La barra rovesciata avvia una sequenza di escape:

// Common escape sequences inside a regular string literal.
string tabbed   = "name:\tAda";          // \t  tab
string twoLines = "line 1\nline 2";      // \n  newline
string quoted   = "She said \"hi\".";    // \"  literal quote
string path     = "C:\\src\\app";        // \\  literal backslash

Console.WriteLine(tabbed);
Console.WriteLine(twoLines);
Console.WriteLine(quoted);
Console.WriteLine(path);

Le sequenze di escape comuni includono \n (nuova riga), \t (tabulazione), \" (virgolette letterali), \\ (barra rovesciata letterale), \0 (char null) e escape Unicode (\uXXXX, \UXXXXXXXX).

A partire da C# 13, \e rappresenta il carattere di controllo ESC (U+001B). Si tratta del byte iniziale per le sequenze di escape del terminale ANSI:

// Beginning in C# 13, \e represents the ESC control character (U+001B).
// It's used to start ANSI terminal escape sequences.
string esc = "\e[31mError\e[0m: file missing";

Console.WriteLine(esc);                  // ESC[31mError ESC[0m: file missing
Console.WriteLine((int)'\e');          // 27

Usare un valore letterale normale quando il testo è breve e contiene solo una manciata di sequenze di escape. Una volta che i caratteri di escape diventano più numerosi dei caratteri visibili, passa a un letterale verbatim o raw.

Valori letterali verbatim

Un valore letterale verbatim è preceduto da @. Le barre inverse sono interpretate alla lettera, il che è utile per i percorsi di Windows e gli schemi di espressioni regolari:

// A verbatim string literal (@) treats backslashes literally.
// Useful for Windows paths and regular expressions.
string winPath = @"C:\src\app\readme.md";
string pattern = @"\d{3}-\d{4}";

Console.WriteLine(winPath);
Console.WriteLine(pattern);

Per incorporare una virgoletta letterale all'interno di una stringa verbatim, raddoppiarla: @"She said ""hi"".". Le stringhe verbatim possono anche estendersi su più righe fisiche.

I letterali verbatim sono la scelta giusta quando le barre rovesciate fanno parte del contenuto, ma non ci sono molte virgolette incluse. Per il testo multilinea o il contenuto con virgolette, i valori letterali stringa non elaborati sono in genere più chiari.

Letterali di stringa grezza

Per ogni valore letterale che contiene virgolette, barre rovesciate o più righe, preferisci i letterali di stringa non elaborati. Eliminano completamente il rumore di escape, che li rende più adatti per json inline, SQL, XML, modelli regex e blocchi di testo formattati in cui l'origine dovrebbe essere simile all'output:

// Raw string literals use three or more quotes and need no escaping.
// The source looks like the output, which is ideal for inline JSON, SQL, XML, and the like.
string json = """
    {
        "name": "Ada",
        "roles": ["admin", "editor"]
    }
    """;

string sql = """
    SELECT Id, Name
    FROM   Users
    WHERE  Name = 'O''Brien'
    """;

Console.WriteLine(json);
Console.WriteLine(sql);

I valori letterali di stringa non elaborati eliminano praticamente le sequenze di escape e consentono qualsiasi formattazione e uso delle virgolette necessari. Vedere letterali di stringa non elaborati per le regole complete.

Stringhe interpolate

Un $ prefisso trasforma un valore letterale in una stringa interpolata. Le espressioni nei {} fori vengono valutate e i relativi risultati inseriti ed è possibile applicare identificatori di formato standard e allineamento all'interno dei fori. L'interpolazione si combina anche con le altre forme letterali — si usa $@"..." per interpolare un letterale verbatim, oppure $"""...""" per interpolare un letterale di stringa non elaborato per un output con formattazione avanzata:

// The $ prefix evaluates expressions inside { } and inserts their values.
string name = "Ada";
int score = 92;

string greeting = $"Hello, {name}! Your score is {score}.";
// Format specifiers and alignment work inside the holes.
string formatted = $"pi = {Math.PI:F3}, padded = |{name,10}|";

// Combine $ and """ for richly formatted multiline output.
string report = $"""
    Report for {name}
    -----------------
    Score : {score}
    Grade : {(score >= 90 ? "A" : "B")}
    """;

Console.WriteLine(greeting);
Console.WriteLine(formatted);
Console.WriteLine(report);

L'interpolazione è il modo consigliato per comporre stringhe da valori nel codice quotidiano.

Indicizzazione e char

Un string è una sequenza di unità di codice UTF-16. L'indicizzatore restituisce un System.Char, che rappresenta una singola unità di codice UTF-16, non necessariamente un punto di codice Unicode completo. Length restituisce il conteggio delle unità di codice.

// A string is a sequence of UTF-16 code units. s[i] returns one char.
string word = "café";

Console.WriteLine(word.Length);          // 4
Console.WriteLine(word[0]);              // c

foreach (char c in word)
{
    Console.Write($"{c} ");              // c a f é
}
Console.WriteLine();

Per i testi che possono contenere emoji o caratteri al di fuori del Piano Multilingue di Base, iterare per rune usando Rune o per cluster di grafemi usando StringInfo. L'iterazione normale char funziona per la maggior parte del testo occidentale e del contenuto dominante ASCII.

Uguaglianza di stringhe

L'uguaglianza su string confronta le sequenze di caratteri, non i riferimenti:

// String equality compares character sequences, not references.
string left  = "hello";
string right = string.Concat("hel", "lo");

Console.WriteLine(left == right);                                      // True
Console.WriteLine(left.Equals(right, StringComparison.Ordinal));       // True

Per i confronti che devono essere sensibili alle impostazioni locali o alla distinzione tra maiuscole e minuscole, passare un valore StringComparison esplicito. Usare StringComparison.Ordinal per valori di protocollo, identificatori e altro testo non linguistico.

Operazioni di stringa comuni

Usare la tabella seguente come guida rapida alle operazioni di stringa quotidiane in C#:

Categoria Cosa copre
Search Trovare caratteri o sottostringhe, testare prefissi e suffissi
Dividi Suddividere una stringa in sottostringhe sui separatori
Concatena Combinare stringhe : +, interpolazione, Concat, Join
Modify Produrre una copia trasformata - Replace, Trim, Substring
Confrontare Testare l'uguaglianza e l'ordinamento con il diritto StringComparison

L'intera API — ogni overload, ogni metodo — è documentata nel riferimento String.

Vedere anche