2015-01-13 8 views
8

Ich versuche, über schnelle und Schließungen zu lernen. Ich stecke auf diesem Beispiel fest.Verschlüsse nicht verstehen Beispiel in Swift

numbers.map({ 
    (number: Int) -> Int in 
    let result = 3 * number 
    return result 
}) 

Was ist (Nummer: Int) -> Int? Ist es eine Funktion? Wo ist es definiert? https://developer.apple.com/library/ios/documentation/Swift/Conceptual/Swift_Programming_Language/GuidedTour.html#//apple_ref/doc/uid/TP40014097-CH2-ID1

Was macht das Schlüsselwort "in"? Die Dokumente sagen, dass man "die Argumente trennen und den Typ vom Körper zurückgeben soll". Ich bin mir nicht sicher, ob ich das verstehe. Warum wird "in" nicht verwendet, um "let result = 3 * number" von "return result" zu trennen.

+2

Dies ist auch eine gute Einführung in Verschlüsse in Swift: http: //letvargo.mooo.com/a-beginners-guide-to-closures-in-swift/) –

Antwort

28

Verschluss ist nur eine Funktion mit den Parametern in den Klammern bewegt verwenden können, mit dem Schlüsselwort in, um die Parameter vom Funktionskörper zu trennen. Die beiden folgenden Beispiele definieren äquivalente Funktionen:

func myFunc(number: Int) -> Int { 
    let result = 3 * number 
    return result 
} 

let myClosure = { (number: Int) -> Int in 
    let result = 3 * number 
    return result 
} 

Sie können sie tatsächlich rufen beide auf genau die gleiche Art und Weise:

let x = myFunc(2)  // x == 6 
let y = myClosure(2) // y == 6 

Beachten Sie, wie das zweite Beispiel ist genau die gleiche wie die erste, nur in der Im ersten Beispiel liegen die Parameter (number: Int) -> Int außerhalb der Klammern, und im zweiten Beispiel befinden sich die Parameter innerhalb der Klammern, gefolgt vom Schlüsselwort in.

map Werke durch eine Anordnung unter (numbers, im Beispiel), und ein neues Array zu schaffen, das das Ergebnis des Anwendens des Verschlussfunktion auf jedes Element in numbers ist. Wenn also numbers[1, 2, 3] ist, beginnt das obige Beispiel mit 1. Es wird die Closure-Funktion anwenden, die eine 3 erzeugt (weil alles, was es tut, das Element aus dem ersten Array mit 3 multipliziert). Dies geschieht für jedes Element in numbers, bis es ein neues Array erzeugt, [3, 6, 9].

Wenn Sie möchten, können Sie map unter Verwendung der Namen der obigen Funktion oder des obigen Abschlusses aufrufen oder indem Sie es explizit innerhalb von map ausschreiben. Alle der folgenden Beispiele vollständig äquivalent sind:

let numbers = [1, 2, 3] 

// Example 1 
let times3 = numbers.map(myFunc)  // times3 == [3, 6, 9] 

// Example 2 
let timesThree = numbers.map(myClosure) // timesThree == [3, 6, 9] 

// Example 3 
let xThree = numbers.map({ (number: Int) -> Int in 
    let result = 3 * number 
    return result      // xThree == [3, 6, 9] 
}) 

zu beachten, dass Beispiel 3 Die gleichen wie in Beispiel 2, nur in Beispiel 3 der Verschluss innerhalb der map explizit dargelegt, wohingegen in Beispiel 2 der Verschluss zugewiesen wurde auf eine Konstante namens myClosure, und die Konstante wurde map geliefert.

Hoffe, das hilft - Schließungen sind lustig, aber verwirrend.

+0

Ich bin auch mit Schließungen fest, aber Ihre Antwort hilf mir zu verstehen. Danke. –

+0

Hey danke Roman, das hat sicherlich geholfen. Es ist mir jetzt sehr klar. Apples Erklärung war ein bisschen zu steil, um den ersten Versuch zu bestehen. –

+0

Vielen Dank! Es hat mir wirklich geholfen zu verstehen, wie dieses Code-Snippet funktioniert. –

1

Die Funktion Sie aufrufen nimmt einen Verschluss als Parameter:

numbers.map({...}) 

Der Verschluss auf die Funktion zur Verfügung gestellt wird erwartet, um einen Parameter zu erhalten, wenn sie durch die Funktion ausgeführt wird, der Sie angerufen hat. Dieser Parameter wird in der Schließung definiert:

(number: Int) -> Int in 

Sie jetzt den Parameter in den Inhalt des Verschlusses

let result = 3 * number 
    return result 
0

Verschlüsse sind eigenständige Funktionsblöcke, die weitergegeben und in Ihrem Code verwendet werden können.

Syntax:

{(parameterName: ParameterType) -> returnType in 
    //Statements 
} 

Praxisszenario: Wenn der Benutzer Filter anwenden möchten und wollen Werte auswählen, welche mehr als 300 (in diesem Fall) ist, wir können Verschlüsse verwenden, um dies zu achive.

var elements: [Int] = [Int]() //Declaring Empty array 
elements = [1001, 999, 555, 786, 988, 322, 433, 128, 233, 222, 201, 276, 133] 

var filteredElements = elements.map({(num: Int) -> Int? in 
    return num > 300 ? num : nil 
}) 

output: 
[Optional(1001), Optional(999), Optional(555), Optional(786), Optional(988), Optional(322), Optional(433), nil, nil, nil, nil, nil, nil] 

From Below-Code kann man deutlich sehen wir vorbei Schließung elements.map() Funktion.

Verschluss:

{(num: Int) -> Int? in 
     return num > 300 ? num : nil 
    } 

(num:Int) ist Parameter. Int? Wir werden den optionalen Integer-Typ zurückgeben.

Nach in können wir Ihre Logik schreiben.

Sie können mehr über Schließung here lesen.

Verwandte Themen