2014-10-01 5 views
6

Warum in Swift diese legal ist ...Swift assert mit String-Parameter

assert(false, "Unexpected diagnosis: \(diagnosis)"); 

während dies nicht?

let assertString = "Unexpected diagnosis: \(diagnosis)" 
assert(false, assertString); 

Im zweiten Schnipsel, erhalte ich die Fehler ...

nicht 'assert' mit einem Argument Liste vom Typ ‚(BooleanLiteralConvertible, String)

Sicher aufrufen kann, Der zweite Parameter ist in beiden Fällen eine Zeichenfolge.

Antwort

4

Zweiter Parameterparameter wird entweder als message: @autoclosure() -> Str oder _ message: StaticString deklariert. Ich denke, "Unexpected diagnosis: \(diagnosis)" wird als Ausdruck behandelt und von @autoclosure abgeholt, während assertString ist einfach eine String Variable, die nicht in Schließung oder StaticString umgewandelt werden kann.

static func convertFromExtendedGraphemeClusterLiteral(value: StaticString) -> StaticString 
static func convertFromStringLiteral(value: StaticString) -> StaticString 

Ich denke, das erklärt, warum rasche manuelle Note hat, die Sie nicht String-Interpolation in assert() verwenden können, da es keine Unterstützung für StringInterpolationConvertible ist:

StaticString kann nur mit gemacht werden.

+0

Wow! Danke, das ist ziemlich schwer für jemanden mit <24 Stunden Erfahrung in Swift. Ich schätze, es ist ein Nebeneffekt der jahrelangen Arbeit in der "Zeiger" -Welt, dass dies für mich nicht offensichtlich war. Hatte etwas gelesen, indem ich es jetzt verstehe. Vielen Dank – Fittoburst

0

Angebotsformular Dokumentationen:

... (assert()) führen ein traditioneller C-Stil mit einer optionalen Nachricht geltend machen. Verwenden Sie diese Funktion für interne Plausibilitätsprüfungen, die während des Tests aktiv sind, die Leistung des Versandcodes jedoch nicht beeinträchtigen. Informationen zur ungültigen Verwendung in Release-Builds finden Sie unter precondition(_:_:file:line:).

und ich getestet auf Xcode 8, precondition(_:_:file:line:) mit formatiertem Saiten gut funktioniert. z. B .:

precondition(userId.lengthOfBytes(using: .ascii) > 0, "\(userId) is invalid for DBManager.id")