Dispatch após Swift: GCD para 3, 4 e 5 com exemplos

Treinador Online de Python para Iniciantes

Aprenda Python facilmente sem sobrecarga teórica. Resolva tarefas práticas com verificação automática e escreva código diretamente no navegador.

Start Course

Como parar de temer atrasos e amar o GCD em Swift 3, 4 e 5

\n\n

Você já escreveu um código que deveria ser executado após três segundos, mas disparou instantaneamente? Ou, ao contrário, esperou uma eternidade, embora planejasse alguns milissegundos? Familiar? Então você certamente já encontrou o dispatch_after — uma das ferramentas mais populares, mas também mais traiçoeiras do Grand Central Dispatch (GCD).

\n\n

Antigamente, na era do Swift 2 e Objective-C, esse método parecia um feitiço: dispatch_after(dispatch_time(DISPATCH_TIME_NOW, Int64(nanoseconds)), dispatch_get_main_queue()). Mas com a chegada do Swift 3, 4 e 5, a API do GCD foi completamente reescrita. Agora não é apenas uma mudança de nome — é uma nova forma de pensar. Neste artigo, vamos explorar como escrever dispatch_after em Swift em todas as versões atuais, desmistificar mitos e fornecer soluções prontas. Vamos lá!

\n\n

O que aconteceu com o dispatch_after? Uma breve história de dor

\n

Antes do Swift 3, os desenvolvedores usavam o GCD no estilo C:

\n
let delay = dispatch_time(DISPATCH_TIME_NOW, Int64(2.0 * Double(NSEC_PER_SEC)))\ndispatch_after(delay, dispatch_get_main_queue()) {\n    print("Olá do passado!")\n}
\n

Isso funcionava, mas era complicado. No Swift 3, a Apple decidiu "swiftificar" o GCD, transformando-o em uma API orientada a objetos. Agora, o dispatch_after se tornou o método asyncAfter da estrutura DispatchQueue. E isso não é apenas uma reforma cosmética — é uma sintaxe completamente nova que exige compreensão.

\n\n

Receita básica: asyncAfter em Swift 3, 4 e 5

\n

Independentemente da versão do Swift (3, 4 ou 5), a sintaxe básica do dispatch_after agora é a mesma. Aqui está o exemplo mais simples de execução atrasada na thread principal:

\n\n
let delayInSeconds: Double = 2.0\nDispatchQueue.main.asyncAfter(deadline: .now() + delayInSeconds) {\n    print("2 segundos se passaram!")\n}
\n

Pontos-chave:

\n
    \n
  • DispatchQueue.main — thread principal (UI).
  • \n
  • .now() + delayInSeconds — criamos um deadline (prazo final) relativo ao momento atual.
  • \n
  • asyncAfter — execução assíncrona após o tempo especificado.
  • \n
\n

Este código funciona no Swift 3.0, 4.0 e 5.0 sem alterações. A mágica é que a Apple manteve esta API estável desde 2016.

\n\n

E o dispatch_time? Trabalhando com nanossegundos

\n

Às vezes você precisa especificar um atraso em nanossegundos (por exemplo, para temporizadores precisos ou lógica de jogos). Na nova API, usa-se DispatchTime:

\n
let nanoseconds: Int = 1_500_000_000 // 1.5 segundos\nlet deadline = DispatchTime.now() + .nanoseconds(nanoseconds)\nDispatchQueue.global().asyncAfter(deadline: deadline) {\n    print("Executado após 1.5 segundos na thread de fundo")\n}
\n

Você também pode usar constantes prontas: .seconds(5), .milliseconds(500) e até .microseconds(1000). Isso é mais conveniente do que multiplicar por NSEC_PER_SEC.

\n\n

Perguntas frequentes (e respostas!) sobre dispatch_after em Swift

\n

No Stack Overflow, esta pergunta acumulou milhares de visualizações. Aqui estão os erros mais comuns que os iniciantes cometem.

\n\n

1. Por que meu código é executado imediatamente, e não com atraso?

\n

O erro mais comum é a confusão entre asyncAfter e async. Se você esqueceu de especificar deadline: ou escreveu DispatchQueue.main.async { ... }, o código será executado imediatamente. A segunda causa: passar um valor negativo. .now() + (-5.0) é um tempo passado, e o GCD executará o bloco imediatamente.

\n\n

2. Como cancelar um dispatch_after?

\n

Ao contrário do Timer, o asyncAfter não possui um método cancel() embutido. Mas existem duas soluções:

\n
    \n
  • Flag de cancelamento: Use um Dispatc

Blogs

Book Recommendations