Einige Gesamtperspektiven, um die anderen nützlichen, aber detaillierteren Antworten zu ergänzen:
In Swift wird das Ausrufezeichen in mehreren Kontexten angezeigt:
- Erzwungenes Auspacken:
let name = nameLabel!.text
- Implizit ausgepackte Optionen:
var logo: UIImageView!
- Zwangsguss:
logo.image = thing as! UIImage
- Unbehandelte Ausnahmen:
try! NSJSONSerialization.JSONObjectWithData(data, [])
Jedes von diesen ist ein anderes Sprachkonstrukt mit einer anderen Bedeutung, aber alle haben drei wichtige Dinge gemeinsam:
1. Ausrufezeichen umgehen die Sicherheitsüberprüfungen zur Kompilierungszeit von Swift.
Wenn Sie !
in Swift verwenden, sagen Sie im Wesentlichen: "Hey, Compiler, ich weiß, dass Sie denken , dass hier ein Fehler auftreten könnte , aber ich weiß mit absoluter Sicherheit, dass dies niemals der Fall sein wird."
Nicht jeder gültige Code passt in das Feld des Swift-Typsystems zur Kompilierungszeit - oder in die statische Typprüfung einer Sprache. Es gibt Situationen, in denen Sie logisch beweisen können, dass ein Fehler niemals auftreten wird, aber Sie können ihn dem Compiler nicht beweisen . Aus diesem Grund haben die Designer von Swift diese Funktionen in erster Linie hinzugefügt.
Wenn Sie jedoch verwenden !
, schließen Sie einen Wiederherstellungspfad für einen Fehler aus, was bedeutet, dass…
2. Ausrufezeichen sind mögliche Abstürze.
Ein Ausrufezeichen lautet außerdem: "Hey Swift, ich bin mir so sicher, dass dieser Fehler niemals auftreten kann, dass es für Sie besser ist, meine gesamte App zum Absturz zu bringen, als für mich, einen Wiederherstellungspfad dafür zu codieren."
Das ist eine gefährliche Behauptung. Es kann das Richtige sein: In geschäftskritischem Code, in dem Sie über die Invarianten Ihres Codes nachgedacht haben, kann es sein, dass eine falsche Ausgabe schlechter ist als ein Absturz.
Wenn ich jedoch !
in freier Wildbahn sehe , wird es selten so achtsam verwendet. Stattdessen bedeutet es zu oft: "Dieser Wert war optional und ich habe nicht wirklich darüber nachgedacht, warum es Null sein könnte oder wie ich mit dieser Situation richtig umgehen soll, aber durch Hinzufügen !
wurde es kompiliert ... also ist mein Code korrekt, oder?"
Passen Sie auf die Arroganz des Ausrufezeichens auf. Stattdessen…
3. Ausrufezeichen werden am besten sparsam verwendet.
Jedes dieser !
Konstrukte hat ein ?
Gegenstück, das Sie zwingt, sich mit dem Fehler / Null-Fall zu befassen:
- Bedingtes Auspacken:
if let name = nameLabel?.text { ... }
- Optionale Optionen:
var logo: UIImageView?
- Bedingte Besetzungen:
logo.image = thing as? UIImage
- Null-bei-Fehler-Ausnahmen:
try? NSJSONSerialization.JSONObjectWithData(data, [])
Wenn Sie versucht sind, zu verwenden !
, ist es immer gut, sorgfältig zu überlegen, warum Sie nicht ?
stattdessen verwenden. Ist ein Absturz Ihres Programms wirklich die beste Option, wenn der !
Vorgang fehlschlägt? Warum ist dieser Wert optional / fehlgeschlagen?
Gibt es einen vernünftigen Wiederherstellungspfad, den Ihr Code im Fall Null / Fehler einschlagen könnte? Wenn ja, codieren Sie es.
Wenn es unmöglich Null sein kann, wenn der Fehler niemals auftreten kann, gibt es dann eine vernünftige Möglichkeit, Ihre Logik zu überarbeiten, damit der Compiler das weiß? Wenn ja, mach es; Ihr Code ist weniger fehleranfällig.
Es gibt Zeiten, in denen es keinen vernünftigen Weg gibt, einen Fehler zu behandeln, und das einfache Ignorieren des Fehlers - und damit das Vorgehen mit falschen Daten - wäre schlimmer als ein Absturz. Dies sind die Zeiten, in denen Gewalt ausgepackt wird.
Ich durchsuche regelmäßig meine gesamte Codebasis !
und überprüfe jede Verwendung davon. Nur sehr wenige Verwendungen halten einer Prüfung stand. (Zum jetzigen Zeitpunkt enthält das gesamte Siesta-Framework genau zwei Instanzen .)
Das heißt nicht, dass Sie Ihren Code niemals verwenden sollten !
- nur, dass Sie ihn achtsam verwenden und ihn niemals zur Standardoption machen sollten.