Ich verstehe, dass beide einen NSMutableString erstellen, nur der erste gehört dem System und der zweite gehört mir (d. h. ich muss ihn freigeben). Gibt es einen bestimmten Grund, warum ich das eine oder das andere verwenden sollte? Auf den ersten Blick erscheint es einfacher, das erste zu verwenden? Auch ist das erste besser, da es dem Compiler ein Gefühl der Größe gibt?
%Vor%ODER
%Vor%BEARBEITEN ... AUCH
Ich sehe viele Deklarationen, die in zwei Zeilen geschrieben sind (d. h.)
%Vor%Persönlich bevorzuge ich den One-Liner, ist das nur ein weiteres Beispiel persönlichen Stil?
%Vor%ODER
%Vor%Gibt es einen bestimmten Grund, warum ich das eine oder das andere verwenden sollte? Auf den ersten Blick scheint es einfacher zu sein, das erste zu verwenden?
Ja. Autorelease immer sofort, es sei denn, Sie haben einen bestimmten Grund nicht.
Der erste Grund ist, dass es sehr leicht ist, die Nachricht release
zu vergessen. Wenn Sie das Objekt in der gleichen Anweisung, in der Sie es erstellt haben, automatisch freigeben (wie in [[[… alloc] init] autorelease]
), ist es viel schwieriger, es zu vergessen und viel offensichtlicher, wenn Sie es tun. Die Convenience-Factory-Methoden (z. B. stringWithCapacity:
) geben das Objekt für Sie automatisch frei. Sie müssen sich also nicht darum sorgen, dass Sie es später freigeben, wenn Sie es selbst freigeben.
Zweitens, selbst wenn Sie daran denken, die separate Nachricht release
zu schreiben, ist es einfach, sie nicht zu treffen. Zwei Möglichkeiten sind frühe Rückkehr:
und geworfene oder propagierte Ausnahmen:
%Vor%Der "spezielle Grund, nicht zu" besteht in der Regel darin, dass Sie eine enge Schleife haben, die viele Objekte erzeugt. In diesem Fall sollten Sie möglichst viele der Objekte in der Schleife manuell verwalten, um sie zu behalten Ihr Objekt zählt herunter. Jedoch tun das nur, wenn Sie Beweise haben, dass dies Ihr Problem ist (seien es harte Zahlen von Shark, harte Zahlen von Instrumenten oder Ihr System geht in die Hölle, wenn diese Schleife lange genug läuft) / p>
Andere, möglicherweise bessere Lösungen bestehen darin, die Schleife in zwei verschachtelte Schleifen aufzuteilen (die äußere, um einen Autorelease-Pool für die innere Schleife zu erstellen und zu entladen) und zu NSOperation zu wechseln. (Stellen Sie jedoch sicher, dass Sie festlegen, wie viele Vorgänge die Warteschlange gleichzeitig ausführen soll. Andernfalls du machst es vielleicht noch leichter, in die Paging-Hölle zu gehen .
Auch ist das erste besser, da es dem Compiler ein Gefühl der Größe gibt?
Es ist besser, aber nicht aus diesem Grund.
Für den Compiler ist es nur eine weitere Klassennachricht. Der Compiler weiß nicht, was es tut; Für alles, was es weiß und interessiert, ist stringWithCapacity:
die Nachricht, um dem Benutzer ein Lied abzuspielen.
Es gibt NSMutableString einen Größenhinweis - die Klasse weiß, wie viel Zeichenspeicher sie anfangs zuweisen möchte. Welchen Nutzen Sie daraus ziehen, ist wahrscheinlich klein (zumindest auf dem Mac), aber wenn Sie die Informationen zur Hand haben, warum nicht verwenden? Umgekehrt würde ich nicht aus dem Weg gehen, um es zu berechnen.
Ich sehe viele Deklarationen, die in zwei Zeilen geschrieben sind (d. h.)
%Vor%Persönlich bevorzuge ich den One-Liner, ist das nur ein weiteres Beispiel persönlichen Stil?
Ja. Es besteht jedoch ein gewisses Risiko, dass eine Variable nicht initialisiert wird. Aktivieren Sie die Build-Einstellung "Static Analyzer starten" auf jeden Fall, wenn Sie sich dazu entscheiden.
Ersteres ist nicht unbedingt für den Compiler, sondern eher ein Vorschlag an den String, wie er das Speichern seiner Daten optimieren könnte. Dies ist am nützlichsten für NSDictionary / NSArray / NSSet, die die Möglichkeit haben, ihre Implementierungen intern je nach dem zu ändern Größe ihres Datensatzes .
Abgesehen davon haben Sie Recht: Der einzige Unterschied ist eine Eigentumsfrage. Ich benutze fast nie die WithCapacity
-Methoden und stattdessen einfach [NSMutableString string]
oder [NSMutableArray array]
, aber IMO, es ist wirklich nur eine Frage des Stils und du wirst nichts gewinnen oder verlieren, indem du eins über das andere verwendest.
Die erste ist eine automatisch freigegebene Zeichenfolge. Dies wird vom System an einem geeigneten Punkt freigegeben. Es wird dem Autorelease-Pool hinzugefügt, und der Speicher wird vom System verarbeitet. Sobald es außerhalb des Geltungsbereichs liegt, können Sie nicht feststellen, dass es gültig ist. Dieser Typ ist nützlich, wenn er nur einen Bereich innerhalb der Methode und auch Werte aus Methoden enthält.
Die zweite wird beibehalten, hat also einen Referenzzähler von 1 und wird nicht zum Autorelease-Pool hinzugefügt. Sie sind dafür verantwortlich, es freizugeben und den Speicher freizugeben. Verwenden Sie diese Methode, wenn Sie den Umfang des Objekts steuern möchten. Wird für Elementvariablen usw. verwendet.
Ich glaube, dass die 2-Zeilen-Initialisierung nur Stil ist, aber ich würde die 2-Zeilen-Variante nicht verwenden, da Sie die Variable definieren, ohne einen Wert dafür zu vergeben, obwohl Sie in der nächsten Zeile sind. Ich denke, diese Art von Variablen Member Deklaration / Initialisierung, aber ich persönlich mag es nicht viel.
Du bringst gültige Fragen auf. Es hängt wirklich davon ab, was du tust, aber für allgemeine iPhone Apps würde ich sagen, benutze einfach die erste. Dies wird automatisch für Sie bereinigt, wenn der Referenzzähler auf 0 steht und Sie sich nicht darum kümmern müssen.
Verwenden Sie die zweite, wenn Sie wirklich einen guten Grund haben, das Speicher der Zeichenfolge selbst zu verwalten. So wie Sie sicher sein möchten, wenn die Zeichenfolge bereinigt werden sollte, oder Sie erwarten, dass der Speicher zu einem bestimmten Zeitpunkt minimal ist.
Ich würde sagen, dass die zweite Regel in der Regel verwendet wird, wenn Sie einen guten Grund dafür haben.
Sie haben Recht bei all Ihren Punkten!
Ich bin nicht sicher, wie groß der Unterschied zwischen dem Größen- / Kapazitätshinweis ist, aber mehr Informationen sollten sicherlich ermöglichen, dass die Laufzeit bessere Entscheidungen trifft.
Warum einen Stil gegenüber dem anderen verwenden? Wann werden automatisch freigegebene Objekte veröffentlicht? Es gibt zwei nicht offensichtliche Gründe, warum es wichtig sein könnte. Erstens, wenn eine Methode viel Speicher verwendet, den Sie sofort freigeben können. (Sie könnten auch einen lokalen Autorelease-Pool verwenden, denke ich.) Zweitens finde ich, dass die Verwendung von AutoRelease Speicherlecks verstecken und das Debugging von Code erschweren kann. Ihre Laufleistung kann je nach Alter und Qualität des Codes variieren.
Als ich anfing, iPhone Apps zu entwickeln, benutzte ich ständig wieder freigegebene Objekte. Es war praktisch, weil ich nicht ganz verstanden habe, wie alles funktioniert hat und es normalerweise das Richtige getan hat. Heutzutage tendiere ich eher dazu, Speicher manuell freizugeben. Es ist wirklich nicht so schwer, wenn Sie tatsächlich verstehen, wie die Referenzzählung funktioniert, und das Problem sofort erzwingt, wenn Sie dies nicht tun.
Wenn Sie sich ziemlich sicher sind, wie lange Sie eine Zeichenfolge benötigen, fahren Sie fort und verwenden Sie die Methode -initWithCapacity:. Wenn Sie den Speicher eines Strings überschreiten, wird er neu zugewiesen und kopiert, was keine billige Operation ist.
Tags und Links objective-c cocoa nsmutablestring