A resposta real é: porque você não pode confiar no adiamento.
No conceito, adiar e assíncrono diferem da seguinte forma:
assíncrono permite que o script seja baixado em segundo plano sem bloquear. Em seguida, no momento em que termina o download, a renderização é bloqueada e esse script é executado. A renderização é retomada quando o script é executado.
adiar faz o mesmo, exceto reivindicações para garantir que os scripts sejam executados na ordem em que foram especificados na página e que serão executados após o término da análise do documento. Portanto, alguns scripts podem terminar o download e aguardar os scripts que foram baixados mais tarde, mas que apareceram antes deles.
Infelizmente, devido ao que é realmente uma briga de gato de padrões, a definição de adiamento varia de especificação para especificação, e mesmo nas especificações mais recentes não oferece uma garantia útil. Como as respostas aqui e esse problema demonstram, os navegadores implementam o adiamento de maneira diferente:
- Em certas situações, alguns navegadores têm um bug que causa a falha
defer
de execução dos scripts.
- Alguns navegadores atrasam o
DOMContentLoaded
evento até depois que os defer
scripts foram carregados, e outros não.
- Alguns navegadores obedecem
defer
a <script>
elementos com código embutido e sem src
atributo, e outros o ignoram.
Felizmente, a especificação especifica pelo menos que as substituições assíncronas sejam adiadas. Assim, você pode tratar todos os scripts como assíncronos e obter uma ampla variedade de suporte ao navegador da seguinte forma:
<script defer async src="..."></script>
98% dos navegadores em uso no mundo todo e 99% nos EUA evitarão o bloqueio com essa abordagem.
(Se você precisar esperar até que o documento termine de analisar, ouça o evento do DOMContentLoaded
evento ou use a .ready()
função útil do jQuery . Você desejaria fazer isso de qualquer maneira para voltar normalmente aos navegadores que não são implementados defer
.)