Ist String ein Werttyp oder ein Referenztyp?

Ist String ein Werttyp oder ein Referenztyp?

Ich kann einfach keine “gute” Erklärung dafür finden …

 Console.WriteLine(typeof(string).IsClass); // true 

Es ist ein Referenztyp.

Es kann kein Werttyp sein, da Werttypen eine bekannte Größe für den Stapel usw. benötigen. Als Referenztyp ist die Größe des Verweises im Voraus bekannt, auch wenn die Größe des Strings nicht gleich ist.

Es verhält sich so, wie Sie erwarten, dass sich ein Werttyp verhält, weil er unveränderlich ist. dh es ändert sich nicht * wenn es einmal erstellt wurde. Aber es gibt viele andere unveränderliche Referenztypen. Delegieren von Instanzen zum Beispiel.

* = außer innerhalb von StringBuilder , aber Sie sehen es nie, während es das tut …

String ist ein unveränderlicher Referenztyp.

Sehen Sie den Blog-Beitrag Unveränderliche Typen: Verstehen Sie ihre Vorteile und verwenden Sie sie auf Unveränderlichkeit.

String ist ein Referenztyp .

Die grundlegende “Erklärung” basiert auf “was” tatsächlich in dem Speicherplatz gespeichert wird, der zugewiesen wird, wenn Sie die Variable für das Ding “deklarieren”. Wenn der tatsächliche Wert der Sache an dem Speicherort gespeichert wird, auf den sich der Variablenname bezieht, handelt es sich um einen Werttyp.

  int x; // memory allocated to hold Value of x, default value assigned of zero 

Wenn, otoh, der Speicherbereich, der zugewiesen wird, wenn Sie die Variable “deklarieren”, nur eine andere Speicheradresse enthält, in der der tatsächliche Wert (oder die Werte) gespeichert wird, dann ist dies ein Referenztyp.

  MyClass x; // Memory allocated to hold an address, // default address of null (0) assigned. // NO MEMORY ALLOCATED for x itself 

oder, wenn die Deklaration die Initialisierung beinhaltet,

  MyClass x = new MyClass(); // Now, Memory slot (call it Addr1) is allocated to hold address of x, // more memory (call it Addr2) is allocated to hold a new MyClass object. // New MyClass object created, stored in memory Addr2 (on the Heap) // Address of new object (Addr2) is stored in Addr1 

Bei einer Zeichenfolge wird die Zeichenfolge auf dem Heap erstellt, und ihre Adresse wird in den Speicherbereich übernommen, der für die Variable reserviert ist. Daher handelt es sich um einen Referenztyp.

String ist ein unveränderlicher Referenztyp, der bestimmte Eigenschaften aufweist, die ihn gelegentlich als Werttyp erscheinen lassen

Der Zeichenfolientyp repräsentiert eine Sequenz von null oder mehr Unicode-Zeichen. string ist ein Alias ​​für String in .NET Framework.

Obwohl String ein Referenztyp ist, sind die Gleichheitsoperatoren (== und! =) So definiert, dass sie die Werte von String-Objekten vergleichen, nicht Referenzen. Dies macht das Testen der Zeichenfolgengleichheit intuitiver. Beispielsweise:

 string a = "hello"; string b = "h"; // Append to contents of 'b' b += "ello"; Console.WriteLine(a == b); Console.WriteLine((object)a == (object)b); 

Dies zeigt “True” und dann “False” an, da der Inhalt der Strings äquivalent ist, aber a und b nicht auf dieselbe String-Instanz verweisen.

Zeichenfolgen sind unveränderlich – der Inhalt eines Zeichenfolgenobjekts kann nicht geändert werden, nachdem das Objekt erstellt wurde, obwohl die Syntax es so aussehen lässt, als ob Sie dies tun könnten. Wenn Sie beispielsweise diesen Code schreiben, erstellt der Compiler tatsächlich ein neues Zeichenfolgenobjekt, das die neue Zeichenfolge enthält, und dieses neue Objekt wird b zugewiesen. Die Zeichenfolge “h” ist dann für die Speicherbereinigung geeignet.

 string b = "h"; b += "ello"; 

In vielen Sprachen gibt es zwei allgemeine Arten von Dingen: solche, bei denen ein Speicherort eines definierten Typs tatsächlich ein Objekt dieses Typs enthält, und solche, bei denen ein Speicherort eines definierten Typs einen Verweis auf ein Objekt dieses Typs enthält welches an anderer Stelle gespeichert wird. Es gibt auch eine Reihe von Arten von Semantik, die Dinge bieten können:

  1. Unveränderbare Wert Semantik: Instanzen eines bestimmten Typs haben eine Eigenschaft (“der Wert”), die die Grundlage der Identität bildet. Zwei Elemente, deren Wert gleich ist, können unabhängig davon, wo sie gespeichert sind, synonym verwendet werden. Der Wert wird konstant sein, solange die Instanz existiert. Eine Variable dieses Typs kann ihren Wert ändern, jedoch nur durch Speichern einer anderen Instanz in der Variablen.
  2. Unveränderbare Referenzsemantik: Im Allgemeinen ähnlich der Semantik des unveränderlichen Werts, außer dass zwei Instanzen, die zu unterschiedlichen Zeiten erstellt wurden, sich selbst als unterschiedliche Instanzen melden.
  3. Veränderbare Wert-Semantik: Instanzen eines bestimmten Typs haben ein Merkmal oder eine Sammlung von Merkmalen (“die Werte”), die die Grundlage der Identität bilden, aber diese Merkmale können geändert werden, ohne die gesamte Instanz zu ersetzen. Jede Instanz wird in genau einer Variablen oder einem Feld gespeichert; Wenn Sie eine Variable oder ein Feld in ein anderes kopieren, werden alle Werte von der ersten Instanz in die zweite kopiert, die Instanzen bleiben jedoch getrennt. Zukünftige Änderungen an einer Instanz wirken sich nicht auf die andere aus.
  4. Veränderbare Referenzsemantik: Jede Instanz ist mit sich selbst identisch, aber mit keiner anderen Entität, und Instanzen haben einen oder mehrere Werte, die in vorhandenen Instanzen geändert werden können. Eine beliebige Anzahl von Variablen oder Feldern kann einen Verweis auf eine beliebige Instanz enthalten. Wenn Sie eine oder eine Feldvariable in eine andere kopieren, wird die zweite auf die gleiche Instanz wie die erste verweisen. Folglich wird jede Änderung an der Instanz, auf die sich eine der Variablen bezieht, die Instanz beeinflussen, auf die sich die andere bezieht (dh dieselbe Instanz).

In einigen Programmiersprachen wie C ++ ist es möglich, sowohl direkt gespeicherte als auch indirekte Referenztypen beliebige der obigen vier Arten von Semantik zu implementieren. In .net und C # implementieren direkt gespeicherte Typen mit exponierten Feldern immer # 3, classnarten mit exponierten Feldern implementieren immer # 4, andere Werttypen können beliebige der obigen implementieren, und andere Referenztypen können # 1, # 2 implementieren. oder # 4, aber nicht # 3, mit einer nur leicht undichten Abstraktion. Zeichenfolgen implementieren # 1.

Vielleicht hilft dir der Artikel Strings in .NET und C # . Laut diesem Artikel ist string ein Referenztyp.