Menu
Coddy logo textTech

Closures finales

Fait partie de la section Logique et Flux du Journey Swift de Coddy — leçon 39 sur 56.

Lorsqu'une closure est le dernier argument d'une fonction, vous pouvez l'écrire à l'extérieur des parenthèses. Il s'agit de la forme trailing-closure, et c'est ainsi que le code Swift se lit naturellement.

let nums = [1, 2, 3]
// Forme standard
let a = nums.map({ $0 * 2 })
// Forme avec fermeture traînante
let b = nums.map { $0 * 2 }

Si la closure est le seul argument, les parenthèses disparaissent également. C'est pourquoi tout ce que vous avez vu jusqu'à présent se lit comme une structure de contrôle personnalisée.

Vous pouvez écrire vos propres fonctions pour accepter des fermetures (closures) de la même manière :

func repeatN(_ n: Int, action: () -> Void) {
    for _ in 0..<n {
        action()
    }
}
repeatN(3) {
    print("hi")
}

La syntaxe de fermeture traînante (trailing-closure) fait que repeatN(3) { ... } se lit comme une boucle intégrée. C'est tout l'intérêt : les structures de contrôle que vous construisez vous-même ressemblent exactement à celles de la bibliothèque standard.

challenge icon

Défi

Facile

Définissez une fonction collect qui :

  • Prend un entier n et une closure builder: (Int) -> String
  • Appelle builder pour chaque i de 1 à n (inclus) et renvoie le tableau des chaînes de caractères résultantes

Lisez un entier depuis stdin, appelez collect avec cet entier en utilisant une closure traînante (trailing closure) qui produit "i=<i>" pour chaque valeur, et affichez le résultat joint par ,.

Pour l'entrée 4, la sortie est i=1,i=2,i=3,i=4.

Aide-mémoire

Syntaxe de fermeture de fin (trailing closure) : lorsqu'une fermeture est le dernier argument, elle peut être écrite à l'extérieur des parenthèses. S'il s'agit du seul argument, les parenthèses sont entièrement omises.

let nums = [1, 2, 3]
let a = nums.map({ $0 * 2 }) // standard
let b = nums.map { $0 * 2 }  // fermeture de fin

Les fonctions personnalisées peuvent accepter des fermetures de la même manière, ce qui permet de les lire comme des structures de contrôle intégrées :

func repeatN(_ n: Int, action: () -> Void) {
    for _ in 0..<n {
        action()
    }
}
repeatN(3) {
    print("hi")
}

Essayez vous-même

let n = Int(readLine()!)!

// TODO: func collect(_ n:Int, builder:(Int)->String) -> [String]
// ensuite appeler collect(n) { ... } et afficher le résultat joint par ","
quiz iconTestez-vous

Cette leçon comprend un petit quiz. Commencez la leçon pour y répondre et suivre votre progression.

Toutes les leçons de Logique et Flux