Как отменить Task в Swift?

«Как отменить Task в Swift?» — вопрос из категории Многопоточность, который задают на 10% собеседований IOS Разработчик. Ниже — развёрнутый ответ с разбором ключевых моментов.

Ответ

Да, Task можно отменить, используя механизм CancellationToken.

Основной подход:

  1. Создайте CancellationTokenSource.
  2. Передайте cancellationToken в задачу.
  3. Задача должна периодически проверять статус отмены.
  4. Вызовите cancel() для инициации отмены.

Пример создания и отмены задачи:

let tokenSource = CancellationTokenSource()
let task = Task {
    // Периодически проверяем отмену
    for i in 1...10 {
        try Task.checkCancellation() // Выбрасывает CancellationError при отмене
        print("Processing item (i)")
        try await Task.sleep(nanoseconds: 1_000_000_000)
    }
}

// Через 3 секунды отменяем задачу
Task {
    try await Task.sleep(nanoseconds: 3_000_000_000)
    tokenSource.cancel()
    print("Task cancellation requested")
}

Ключевые моменты:

  • Отмена кооперативная — задача должна явно проверять Task.isCancelled или вызывать Task.checkCancellation().
  • Состояние задачи — после отмены task.isCancelled будет true, но task.isCompleted станет true только после завершения работы задачи.
  • Очистка ресурсов — используйте defer или Task.checkCancellation() для корректного освобождения ресурсов при отмене.

Проверка отмены вручную:

Task {
    while !Task.isCancelled {
        // Выполняем работу
        await processNextItem()
    }
    // Выполняем финализацию
    cleanupResources()
}