Ich bin neu in der objektorientierten Programmierung, und ein Konzept, das mich lange beschäftigt hat, ist Unveränderlichkeit. Ich glaube, die Glühbirne ist letzte Nacht ausgegangen, aber ich möchte Folgendes überprüfen:
Wenn ich auf Aussagen stoße, dass ein unveränderliches Objekt nicht geändert werden kann, bin ich verwirrt, weil ich zum Beispiel Folgendes tun kann:
NSString *myName = @"Bob";
myName = @"Mike";
Dort habe ich gerade meinen Namen vom unveränderlichen Typ NSString geändert. Mein Problem ist, dass sich das Wort "Objekt" auf das physische Objekt im Speicher oder die Abstraktion "meinName" beziehen kann. Die erstere Definition gilt für den Begriff der Unveränderlichkeit.
Was die Variable betrifft, so ist eine (für mich) klarere Definition der Unveränderlichkeit, dass der Wert eines unveränderlichen Objekts nur geändert werden kann, indem auch seine Position im Speicher, dh seine Referenz (auch als Zeiger bezeichnet), geändert wird.
Ist das richtig oder bin ich noch im Wald verloren?
quelle
NSString
, es ist ein " Zeiger auf undNSString
", der nicht unveränderlich ist. Ich weiß nichts über Ziel C, aber ich vermute in Ihrem Beispiel,@"Mike"
dass eine neue Instanz von erstelltNSString
und dem Zeiger zugewiesen wirdmyName
. Sie haben also nicht das Objekt geändert, auf das verwiesenmyName
wurde, sondern nur das, auf das verwiesen wurde.Antworten:
Es hört sich so an, als würden Sie in die richtige Richtung gehen, haben es aber noch nicht ganz verstanden. Das ist falsch:
In Ihrem Code-Snippet
myName
handelt es sich nicht um einen unveränderlichen TypNSString
, sondern um einen veränderlichen TypNSString*
(Zeiger auf NSString). Es hört sich so an, als ob der Schlüssel, den Sie vermissen, darin besteht, zu verstehen, dass ein Zeiger nur ein anderer Wert ist und dass er ein völlig anderes Leben hat als das, auf das er zeigt (oder Dinge, wenn Sie ihn im Laufe seines Lebens teilweise ändern).Du sagst:
Das ist falsch. Ein Objekt nicht besitzen die Zeiger dieser Punkt auf sie, noch ist eine Speicherstelle des Objekts gesteuert oder auf andere Weise durch irgendwelche Hinweise auf ihr betroffen.
Die beiden
NSString
Objekte in Ihrem Beispiel (@"Bob"
und@"Mike"
) sind also vollständig von dermyName
Variablen getrennt. Sie sind auch völlig voneinander getrennt. Wenn SiemyName
auf zeigen,@"Mike"
anstatt auf zu zeigen@"Bob"
, ändern Sie dieNSString
Objekte nicht.Der Vollständigkeit halber werde ich bemerken, dass Garbage Collectors dies insofern komplexer machen, als Änderungen an Zeigern sich auf die Objekte auswirken können, auf die sie zeigen (ed). Dies ist jedoch ein Implementierungsdetail, das das beobachtbare Verhalten des Codes nicht beeinflussen sollte.
quelle
Sie sind bei Worten verloren. Unveränderlichkeit bedeutet: Solange Sie die Variable nicht ändern, enthält sie immer den gleichen Wert, unabhängig davon, was Sie mit anderen Variablen tun.
Gegenbeispiel in C (etwas vereinfacht, vorausgesetzt eine Architektur, die das erlaubt):
Jetzt "enthält" a nicht mehr (dh zeigt auf) den String "Hello World", sondern "Yello World".
In Sprachen, in denen Zeichenfolgen unveränderlich sind, wie Java und (EDIT: safe) C #, können Sie dies nicht tun. Auf keinen Fall. Dies bedeutet, dass jeder Teil des Programms einen sicheren Verweis auf den String behalten kann und sich darauf verlassen kann, dass sich dessen Inhalt niemals ändert. Andernfalls müssten sie eine Kopie erstellen, um auf der sicheren Seite zu sein.
Die Variable ist jedoch noch veränderbar. Sie können es auf ein anderes Objekt zeigen lassen. Es ist nur so, dass sich das Objekt selbst nicht hinter deinem Rücken verändert.
quelle
unsafe
Code verwenden.Sie verwechseln Variablen mit Objekten. Variablen können zum Speichern von Referenzen auf Objekte verwendet werden, sie sind jedoch KEINE Objekte. Es sind Objekte, die unveränderlich sind, keine Variablen. Sie können also die Variablen von einem Objekt in ein anderes ändern, aber Sie können die Attribute des Objekts nicht ändern, wenn es unveränderlich ist.
Stellen Sie sich das Objekt als einen lauten, betrunkenen Nachbarn vor. Wenn er vernünftig (veränderlich) ist, können Sie möglicherweise an seine Tür klopfen und ihn in einen Lebensstil verwandeln, in dem er nicht so viel Lärm macht. Aber wenn er unveränderlich ist, besteht Ihre einzige Änderung in der Hoffnung, dass jemand anderes einzieht!
quelle
Eine Variable ist kein Objekt. Eine Variable ist ein Name, der sich auf ein Objekt (oder allgemeiner auf einen Wert) bezieht.
Zum Beispiel ist "der Torhüter" ein Name, mit dem wir uns auf das Objekt (die Person) beziehen, die für die Verteidigung des Tores verantwortlich ist. Aber wenn ich diese Person durch eine andere ersetze (weil die frühere verletzt ist oder so), wird die neue Person jetzt als "Torhüter" bezeichnet.
Die Zuweisungsanweisung macht Variablen veränderbar (einige Sprachen wie Haskell haben sie nicht und verwenden tatsächlich unveränderliche Variablen). Hiermit können Sie die Bedeutung eines Namens neu definieren und den Wert neu zuweisen.
Jetzt Objekte selbst kann unveränderlich sein. Vor ein paar tausend Jahren hätte man sich Diamanten als unveränderlich vorstellen können. Egal, was Sie mit einem Diamanten gemacht haben, Sie konnten ihn nicht ändern. Egal, ob Sie es Waggawooga nannten (was locker "der größte glänzende Stein unseres Stammes" bedeutet) oder nicht mehr so nannten (weil Sie einen größeren gefunden haben), der Diamant blieb derselbe. Im Gegensatz dazu ist das Stück Holz, das Sie früher mit Ihrem Waggawooga in lustige Bilder geschnitzt haben, nicht dasselbe geblieben. Es erwies sich als wandelbar. Auch wenn es die ganze Zeit den gleichen Namen hatte.
Sowohl Variablen als auch Werte können (unabhängig) unveränderlich sein. In diesem Fall sind es die Objekte, die unveränderlich sind. Sobald Sie ein erstellt haben
NSString
, können Sie es nicht mehr ändern. Sie können es benennen und weitergeben, aber es bleibt gleich. Im Gegensatz dazuNSMutableString
kann nach dem Anlegen zB durch Aufruf dersetString
Methode geändert werden.quelle
Ich glaube, Sie fühlen sich verloren, weil Sie zwei Konzepte mischen: das Objekt selbst und den Variablennamen, der an dieses Objekt gebunden ist.
Unveränderliche Objekte können nicht geändert werden. Zeitraum. Variablenname (Symbol), der an ein unveränderliches Objekt gebunden ist, kann jedoch so geändert werden, dass er an ein anderes unveränderliches Objekt gebunden ist .
Mit anderen Worten, was Sie in diesen beiden Zeilen getan haben, war:
myName
an dieses ObjektmyName
an dieses Objektquelle
Ihr Typ ist kein
NSString
" Zeiger auf einenNSString
", der nicht unveränderlich ist. Ich weiß nichts über Ziel C, aber ich vermute in Ihrem Beispiel,@"Mike"
dass eine neue Instanz von erstelltNSString
und dem Zeiger zugewiesen wirdmyName
. So haben Sie das Objekt nicht geändert , dasmyName
war zeigte auf, gerade was es zeigte.quelle
Hier ist ein Beispiel für ein veränderbares Objekt: Ein Array von
char
in C:Ich kann die ändern Inhalt der
str
in mein Herz Inhalt (so lange es nicht mehr als 10 Zeichen). Damit es von den C-String-Bibliotheksfunktionen als String erkannt wird, muss eine nachgestellte 0 vorhanden sein, damit es Strings mit einer Länge von bis zu 9 Zeichen aufnehmen kann:und so weiter .
Vergleichen Sie dies mit einem String-Objekt in Java:
Die String - Instanz (der Teil des Speichers, das die Zeichen ‚H‘ enthält, ‚E‘, ‚L‘, ‚l‘ und ‚o‘) kann nicht verändert werden; Ich kann den Inhalt dieser Zeichenfolge nicht ändern. Wenn du etwas schreibst wie
Sie fügen "World" nicht an das Ende der "Hello" -Instanz an. Sie erstellen eine neue Instanz , kopieren "Hello World" darauf und aktualisieren
foo
, um auf diese neue Zeichenfolgeninstanz zu verweisen.foo
enthält selbst nicht die String-Instanz; Es bezieht sich nur auf diese Instanz (ähnlich einem Zeiger in C oder Obj-C), weshalb Typen wie String als Referenztypen bezeichnet werden.quelle