10.2 String 

Wie in Abschnitt 3.1.9, »Datentypen«, bereits erwähnt wurde, sind Zeichenketten vom Typ String unveränderlich. Bei jeder Änderung wird ein neues Objekt erzeugt. Häufig zu ändernde Zeichenfolgen repräsentieren Sie effizienter mit der Klasse StringBuilder. Um keinen Speicherplatz zu verschwenden, werden String-Literale in einem Pool verwaltet.
10.2.1 Erzeugung 

Die Initialisierung einer Zeichenkette kann durch direkte Zuweisung oder über einen Konstruktor erfolgen, von denen drei häufiger eingesetzt werden:
Dim z As String = "Literal" |
Der erste Konstruktor wiederholt ein Zeichen, die beiden anderen bedienen sich aus einem Zeichenarray.
Dim z1 As String = New Char(){"1"c,"2"c,"3"c,"4"c} 'ergibt "1234"
Dim z2 As New String("x"c, 3) 'ergibt "xxx"
Dim z3 As New String(New Char(){"1"c,"2"c,"3"c,"4"c}) 'ergibt "1234"
Dim z4 As New String(New Char(){"1"c,"2"c,"3"c,"4"c}, 1, 2) 'ergibt "23"
10.2.2 Eigenschaften 

String weist nur zwei Eigenschaften auf: Length und Chars. Length liefert die Anzahl der Zeichen, und mit Chars greifen Sie auf ein einzelnes Zeichen aus der Zeichenfolge zu:
Public ReadOnly Default Property Chars(index As Integer) As Char |
Im folgenden Codefragment wird das Zeichen »L« in c gespeichert:
Dim str As String = "HALLO"
Dim c As Char = str(2)
10.2.3 Methoden 

Die Methoden dienen im Wesentlichen zur Manipulation von Zeichenketten (siehe Tabelle 10.2).
Methode | Beschreibung | |
Clone |
Referenz auf diesen String (keine Kopie) |
|
Compare |
Vergleich zweier Zeichenketten |
S |
CompareOrdinal |
Vergleich zweier Zeichenketten auf Codebasis |
S |
CompareTo |
Vergleich zweier Zeichenketten |
|
Concat |
Zeichenketten zusammenfügen |
S |
Contains |
Gibt an, ob die gegebene Zeichenkette in dieser Zeichenkette vorkommt. |
|
Copy |
Kopie der Zeichenkette |
S |
CopyTo |
Kopie eines Teilstrings in ein Zeichenarray |
|
EndsWith |
Gibt an, ob die gegebene Zeichenkette das Ende dieser Zeichenkette darstellt. |
|
Equals |
Gibt an, ob zwei Zeichenketten gleiche Buchstabenfolgen haben. |
(S) |
Format |
Formatierung ähnlich Write |
S |
GetEnumerator |
»Zähler« zum Durchlaufen in einer Schleife |
|
GetTypeCode |
Gleichnamige Enumeration hat Primitive, Object, DBNull und Empty. |
|
IndexOf |
Erstes Auftreten der gegebenen Zeichenkette in dieser Zeichenkette |
|
IndexOfAny |
Erstes Auftreten der gegebenen Buchstaben in dieser Zeichenkette |
|
Insert |
Einfügen eines Teilstrings |
|
Intern |
Interne Referenz auf diese Zeichenkette (gegebenenfalls in Pool überführt) |
S |
IsInterned |
Referenz auf Pool-String oder Nothing |
S |
IsNormalized |
Gibt an, ob die Zeichenkette in Unicode »Normalform« vorliegt. |
|
IsNullOrEmpty |
Gibt an, ob ein Leerstring oder Nothing vorliegt. |
S |
Join |
Verbinden eines String-Arrays mit gegebenem Separator |
S |
LastIndexOf |
Letztes Auftreten der gegebenen Zeichenkette in dieser Zeichenkette |
|
LastIndexOfAny |
Letztes Auftreten der gegebenen Zeichen in dieser Zeichenkette |
|
Normalize |
Unicode in »Normalform« konvertieren |
|
PadLeft |
Auffüllen von links mit gegebenen Zeichen, bis Länge erreicht ist |
|
PadRight |
Auffüllen von rechts mit gegebenen Zeichen, bis Länge erreicht ist |
|
Remove |
Eine gegebene Anzahl Zeichen löschen |
|
Replace |
Ersetzen von Teilstrings durch gegebene Zeichenfolgen |
|
Split |
String beim Auftreten der gegebenen Zeichen trennen |
|
StartsWith |
Gibt an, ob die gegebene Zeichenkette den Anfang dieser Zeichenkette darstellt. |
|
Substring |
Extraktion eines Teilstrings |
|
ToCharArray |
Kopie von Buchstaben in ein Char-Array |
|
ToLower |
Umwandlung in Kleinbuchstaben |
|
ToLowerInvariant |
Umwandlung in Kleinbuchstaben mit neutraler Kultur |
|
ToUpper |
Umwandlung in Großbuchstaben |
|
ToUpperInvariant |
Umwandlung in Großbuchstaben mit neutraler Kultur |
|
Trim |
Entfernen gegebener Zeichen am Rand |
|
TrimEnd |
Entfernen gegebener Zeichen am rechten Rand |
|
TrimStart |
Entfernen gegebener Zeichen am linken Rand |
Zeichenfolgen-Vergleiche
Die vier Methoden Equals, Compare, CompareTo und CompareOrdinal sind sehr ähnlich. Wie bereits in Abschnitt 6.2.2, »List«, gezeigt wurde, liefert CompareTo einen negativen Wert, wenn die Zeichenketten lexikalisch sortiert sind, und einen positiven Wert, wenn nicht. Bei Gleichheit wird Null zurückgegeben.
Hinweis |
Standardmäßig wird bei String-Variablen zwischen Groß- und Kleinschreibung unterschieden. |
Entscheidend dafür, wann ein Zeichen als größer oder kleiner im Vergleich zu einem zweiten gilt, ist die spezifische Ländereinstellung. Im mitteleuropäischen Sprachraum ist festgelegt, dass den Großbuchstaben ein größerer Wert zugeordnet ist als ihrem kleingeschriebenen Pendant. Compare vergleicht erst Buchstaben und dann die Schreibung:
a < A < b < B < c < C ... < y < Y < z < Z |
CompareOrdinal vergleicht zwei Zeichenfolgen auf Basis der Zeichencodes. Sind alle identisch, gibt die Funktion Null zurück. Sonst gibt sie die Differenz der Codes des ersten unterschiedlichen Buchstabens zurück.
A < B < C ... X < Y < Z ... a < b < c ... x < y < z |
Das folgende Codefragment testet die beiden Vergleiche:
'...\Basisklassen\KlasseString\Vergleich.vb |
Option Strict On
Namespace Basisklassen
Module Vergleich
Sub Vergleichen(ByVal fun As Func(Of String, String, Integer))
For Each s As String In New String() {"A", "a", "E", "e"}
Console.Write("{0}-{1}:{2} ", "C", s, fun("C", s))
Next
Console.WriteLine()
End Sub
Sub Test()
Console.Write("Compare: ")
Vergleichen(AddressOf String.Compare)
Console.Write("CompareOrdinal: ")
Vergleichen(AddressOf String.CompareOrdinal)
Console.ReadLine()
End Sub
End Module
End Namespace
Die Ausgabe zeigt die verschiedene Einsortierung der Kleinbuchstaben:
Compare: C-A:1 C-a:1 C-E:-1 C-e:-1
CompareOrdinal: C-A:2 C-a:-30 C-E:-2 C-e:-34
Suchen in einer Zeichenkette
Es gibt zwei Gruppen von Suchfunktionen. Die Methoden StartsWith, Contains und EndsWith testen, ob ein Teilstring mit einer gegebenen Zeichenfolge übereinstimmt, während IndexOf und LastIndexOf eine konkrete Position liefern, die in den Methoden Substring und Insert verwendet werden kann. Die Länge der beteiligten Zeichenketten ist beliebig, die Suchfunktionen berücksichtigen Groß- und Kleinschreibung. Das folgende Beispiel zeigt einige der Methoden im Einsatz. Die Abbruchbedingung der Schleife nutzt die Rückgabe von -1 der Methode IndexOf, wenn der Teilstring nicht gefunden wird.
'...\Basisklassen\KlasseString\Suchen.vb |
Option Strict On
Namespace Basisklassen
Module Suchen
Sub Test()
Dim str As String = "Da wird der Hund in der Pfanne verrückt."
Console.WriteLine("Start mit Da: {0}", str.StartsWith("Da"))
Dim pos As Integer = –1
Do
pos += 1
pos = str.IndexOf("der", pos)
If pos > 0 Then Console.Write(str.Substring(pos, 7) & " -")
Loop While pos >= 0
Console.WriteLine()
Console.WriteLine("Rest: {0}", str.Substring(str.LastIndexOf("der")))
Console.ReadLine()
End Sub
End Module
End Namespace
Der Satzanfang wird korrekt gefunden, und es werden jeweils 7 Buchstaben lange Teilstrings ausgegeben, die mit »der« beginnen (IndexOf liefert den Beginn der gesuchten Zeichenfolge). Die einparametrige Variante von Substring extrahiert einen Teilstring von der gegebenen Position bis zum Ende der gesamten Zeichenkette.
Start mit Da: True
der Hun -der Pfa -
Rest: der Pfanne verrückt.
Textränder bearbeiten
Leerzeichen sind naturgemäß nicht sichtbar. Bei einer Texteingabe können sie insbesondere am Anfang und Ende der Eingabe leicht übersehen werden. Werden die Eingaben ungefiltert gespeichert und wird später ohne Leerzeichen danach gesucht, sind die Daten »unauffindbar«. Die unerwünschten Zusatzzeichen können Sie mit Trim, TrimStart oder TrimEnd entfernen.
Public Function Trim() As String |
Die Überladungen der Methode entfernen auch andere Zeichen an den Textenden. Im folgenden Codefragment wird das Trennzeichen für Verzeichnisse in einer Pfadangabe entfernt, ganz ohne If-Anweisungen:
Dim str As String = "C:\Temp\ "
Console.WriteLine("""{0}"" -> ""{1}""", str, str.TrimEnd("\ ".ToCharArray()))
Die Ausgabe zeigt die Kürzung:
"C:\Temp\ " -> "C:\Temp"
Der gegenteilige Fall sind fehlende Zeichen an den Textenden. Die Methoden PadLeft und PadRight füllen eine Zeichenkette bis zur angegebenen Länge auf.
Public Function PadLeft(totalWidth As Integer) As String |
Dies ist zum Beispiel für tabellarische Darstellungen praktisch.
For Each z As Double In New Double() {-1.27, 8.24, 12.98, –100.01}
Console.WriteLine(z.ToString().PadLeft(7))
Next
Die Zahlen werden rechtsbündig ausgegeben:
–1,27
8,24
12,98
–100,01
Zeichenfolgen ändern
Neben den drei grundlegenden Änderungsoperationen Einfügen einer Zeichenkette, Löschen von Bereichen und Ersetzen eines Teilstrings durch einen anderen gibt es Methoden, um alle Buchstaben einer Zeichenkette klein- oder großzuschreiben, wobei Kulturabhängigkeiten berücksichtigt werden können.
Public Function Insert(startIndex As Integer, value As String) As String |
Im folgenden Codefragment nutzen wir IndexOf, um die richtige Einfügeposition in Insert für den zweiten Vornamen zu erhalten. Diesen schreiben wir danach durch Ersetzen mit Replace aus bzw. geben den Namen mit ToUpper in Großschreibung aus:
Dim str As String = "James Kirk"
str = str.Insert(str.IndexOf("Kirk"), "T. ")
Console.WriteLine("Kurzform: {0}", str)
Console.WriteLine("Voller Name: {0}", str.Replace("T.", "Tiberius"))
Console.WriteLine("Großgeschrieben: {0}", str.ToUpper())
Die verschiedenen Namensformen werden korrekt ausgegeben:
Kurzform: James T. Kirk
Voller Name: James Tiberius Kirk
Großgeschrieben: JAMES T. KIRK
Daten in Zeichenketten
Programme können nicht alle denkbaren Datenformate speichern, sondern nur die bei der Entwicklung berücksichtigten. So weiß zum Beispiel eine Datenbank in der Regel nichts von einer von Ihnen entwickelten Datenstruktur. Wollen Sie die Daten dennoch in zusammenhängender Form speichern, bietet sich eine Konvertierung in eine Zeichenkette an. Die einzelnen Datenfelder werden durch Zeichen getrennt, die in den Daten selbst nicht vorkommen. Ein einfaches Beispiel ist eine Textverarbeitung, die die Zeilen des Textes zusammenhängend speichert. Das Trennzeichen ist in diesem Fall ein Zeilenvorschub. Am einfachsten setzen Sie die Zeichenkette mit Join zusammen, und Sie zerlegen sie mit Split. In der folgenden Syntax sind optionale Parameter kursiv gesetzt.
Public Shared Function Join(separator As String, value As String(), _ |
Im folgenden Beispiel wird Split im Konstruktor der Klasse Person benutzt, um die Werte der einzelnen Felder zu ermitteln. Das Zusammensetzen für die Ausgabe in ToString übernimmt Join. Ich benutze die Methoden GetFields, GetValue und SetValue aus der Klasse Type, um das Listing kurz zu halten und Ihnen Anregungen für eigene Klassen zu geben.
'...\Basisklassen\KlasseString\Teilen.vb |
Option Strict On
Namespace Basisklassen
Module Teilen
Class Person
Public Name, Straße, Ort As String
Public Sub New(ByVal p As String)
Dim felder() As String = p.Split(";"c)
For nr As Integer = 0 To Me.GetType().GetFields().Length – 1
Me.GetType().GetFields()(nr).SetValue(Me, felder(nr))
Next
End Sub
Public Overrides Function ToString() As String
Return String.Join(";", Me.GetType().GetFields(). _
Select(Function(f) CType(f.GetValue(Me), String)).ToArray())
End Function
End Class
Sub Test()
Dim p As New Person("E. van Haar;Engelsstr. 10;42283 Wuppertal")
Console.WriteLine("Person : {0}", p)
Console.WriteLine("Kontrolle: {0};{1};{2}", p.Name, p.Straße, p.Ort)
Console.ReadLine()
End Sub
End Module
End Namespace
Die ausgegebenen Informationen sind identisch zur Eingabe:
Person : E. van Haar;Engelsstr. 10;42283 Wuppertal
Kontrolle: E. van Haar;Engelsstr. 10;42283 Wuppertal
Wollen Sie die Separatorzeichen lieber selbst einsetzen, können Sie als Alternative zum Verkettungsoperator & die Methode Concat verwenden:
Public Shared Function Concat(ParamArray args As Object()) As String |
Zeichenfolgen und Char-Arrays
Viele Methoden im .NET Framework haben Zeichenketten als Parameter, andere erwarten ein Char-Array. Daher sind Umwandlungen öfter nötig. Der Weg zur Zeichenkette führt über den Konstruktor (siehe Abschnitt 10.2.1, »Erzeugung«). Für die umgekehrte Richtung gibt es eine Methode:
Public Function ToCharArray() As Char() |
Ihre Meinung
Wie hat Ihnen das Openbook gefallen? Wir freuen uns immer über Ihre Rückmeldung. Schreiben Sie uns gerne Ihr Feedback als E-Mail an kommunikation@rheinwerk-verlag.de.