In Objective-C
, wenn Sie NSLog
ein Objekt oder po
it in lldb
haben, erhält das Objekt die Nachricht description
.
In Swift scheint das Verhalten jedoch anders zu sein. Ich habe sowohl Printable
(benötigt description
Eigenschaft) als auch DebugPrintable
implementiert (was wiederum eine Eigenschaft namens debugDescription
benötigt). Wenn ich println()
ein Objekt oder po
es versuche, wird keine dieser Eigenschaften aufgerufen.
Was ist los? Was sind diese Protokolle für dann ??
Es gibt ein bekanntes Problem, dass Printable
von der Swift REPL ignoriert wird (dh alles in einem Playground oder in der Befehlszeile von xcrun swift
ausgeführt wird), aber vom Compiler erkannt wird (compilierte Apps im Simulator oder xcrun swiftc
).
Hier ist zum Beispiel der Code von "foo.swift":
%Vor%Wenn ich es mit der REPL benutze, bekomme ich das:
%Vor% Aber wenn ich es zuerst kompiliere und dann starte, benutzt es die description
berechnete Eigenschaft:
Das Protokoll DebugPrintable
ist nützlich, wenn Sie die Funktionen debugPrint
und debugPrintln
verwenden möchten. Im kompilierten Code wird die debugDescription
-Eigenschaft einer Instanz ausgegeben.
Nur um ein paar mehr Details zu Nates Antwort hinzuzufügen:
in Xcode 6, wenn Sie versuchen, ein Swift-Objekt zu "po", passiert eines von zwei Dingen:
Das Objekt ist tatsächlich ein Objective-C-Objekt (z. B. NSWindow, NSString) oder ein optionaler Typ. In diesem Fall wird LLDB bei Bedarf ausgepackt und ruft dann NSPrintForDebugger (objcpointer) auf. Dies bedeutet, dass ObjC-Objekte in Swift genauso "po" sein sollten wie in Objective-C
Das Objekt ist eigentlich ein Swift-Objekt. In diesem Fall verwendet LLDB seine eigenen Datenformatierer, um das Objekt zu drucken, mit ein paar kleineren Optimierungen, die ein "po" -ähnliches Aussehen ergeben, aber egal welche Protokolle Ihr Objekt implementiert, sie werden ignoriert
Als zukünftige Erweiterung ist die Idee, dass LLDB in der Lage sein wird, die Swift-Standardbibliothek nachDebugString (Objekt) zu fragen und die Swift-Bibliothek die Details der Operationen behandeln zu lassen - ähnlich wie bei NSPrintForDebugger () im Objective- C Welt.
In diesem erweiterten Universum könnte der Vertrag der Standardbibliothek sehr wohl sein, dass die Implementierung von Printable oder DebugPrintable das Ergebnis von toDebugString () beeinflussen würde. LLDB würde sich automatisch durchsetzen, weil es nur die Verantwortung delegiert.
Selbst in solch einem erweiterten Universum wird Ihre Laufleistung im REPL-Modus aufgrund der Einschränkungen des JIT variieren. Die gleiche Einschränkung macht es übrigens unmöglich, einen Typ auf einem Spielplatz zu definieren und seine Darstellung anzupassen (das würde die Implementierung von mindestens einem der Reflectable / Mirror-Protokolle erfordern)
Tags und Links objective-c cocoa swift lldb