Sobes.tech
Middle

Explique la différence entre les closures escaping et non-escaping, et dans quels cas il est nécessaire d'utiliser @escaping.

sobes.tech IA

Réponse de l'IA

Les closures par défaut ne sont pas escapables.

Closure non escapable :

  • S'exécute dans le corps de la fonction à laquelle il est passé.
  • Capture des variables, mais les libère après la fin de la fonction.
  • Ne survit pas à la fonction.
func doSomething(completion: () -> Void) {
    // Appel de completion ici
    completion() 
}

Closure escapable :

  • S'exécute après le retour de la fonction à laquelle il est passé.
  • Survit au corps de la fonction.
  • Peut être stocké pour une exécution ultérieure, par exemple dans un autre thread ou de manière asynchrone.
  • Capture des variables, en maintenant des références fortes, ce qui peut conduire à des cycles de références fortes (cycles de rétention). Nécessite la déclaration explicite @escaping.
class DataManager {
    var completionHandlers: [() -> Void] = []

    func addCompletionHandler(handler: @escaping () -> Void) {
        completionHandlers.append(handler)
    }

    func performTasks() {
        // Exécution des tâches...
        for handler in completionHandlers {
            handler() // Appel des gestionnaires plus tard
        }
    }
}

L'utilisation de @escaping est nécessaire dans les cas suivants :

  • Lorsqu'une closure est stockée dans une propriété d'une classe ou d'une structure.
  • Lorsqu'une closure est passée à un autre thread ou une opération asynchrone (par exemple, requête réseau, GCD, OperationQueue).
  • Lorsqu'une closure est utilisée comme gestionnaire d'événements ou délégué.