1. Definição de função de retorno de chamada
Uma função de retorno de chamada é uma função chamada através de um ponteiro de função. Se você passar no ponteiro (endereço) da função como um argumento para outra função, quando esse ponteiro é usado para chamar a função que aponta, dizemos que esta é uma função de retorno de chamada. A função de retorno de chamada não é chamada diretamente pelo implementador da função, mas é chamada por outra parte quando ocorre um evento ou condição específico e é usado para responder ao evento ou condição.
No JavaScript, a definição específica da função de retorno de chamada é: a função A é passada como um parâmetro (referência da função) em outra função B, e essa função B executa a função A. Digamos que a função A seja chamada de função de retorno de chamada. Se não houver nome (expressão de função), ele é chamado de função de retorno de chamada anônimo. Portanto, o retorno de chamada não é necessariamente usado para assíncrono. Os retornos de chamada são frequentemente usados em cenários gerais de síncrono (bloqueando), como exigir que algumas operações sejam executadas e a função de retorno de chamada seja executada.
exemplo
Um exemplo de uso de retornos de chamada em sincronização (bloqueio) é executar o Func2 após a execução do código Func1.
var func1 = function (retorno de chamada) {// faça algo. (retorno de chamada && typeof (retorno de chamada) === "function") && callback ();} func1 (func2); var func2 = function () {}2. Use ocasiões de função de retorno de chamada
Carregamento de recursos: Execute o retorno de chamada após o carregamento dinâmico de arquivos JS, execute o retorno de chamada após o carregamento do IFRAME, execute o retorno de chamada após carregar o retorno de chamada da operação do AJAX, execute retorno de chamada após carregamento da imagem, Ajax, etc.
Os eventos DOM e os eventos Node.js são baseados no mecanismo de retorno de chamada (os retornos de chamada do Node.js podem ter problemas de ninho de retorno de chamada de várias camadas).
O tempo de atraso do setTimeout é 0. Este hack é frequentemente usado. A função chamada pelo setTimeout é na verdade uma modalidade de retorno de chamada
Chamada de cadeia: Quando a chamada em cadeia, é fácil implementar a chamada de cadeia no método do avaliador (setter) (ou em métodos que não retornam valores), mas o valor getter é relativamente difícil de implementar a chamada de cadeia, porque você precisa do valor getter para retornar os dados necessários em vez desse ponteiro. Se você deseja implementar o método da cadeia, pode usar uma função de retorno de chamada para implementá -lo.
As chamadas de função do setTimeout e SetInterval obtêm seu valor de retorno. Como ambas as funções são assíncronas, ou seja, o tempo de chamada e o principal processo do programa são relativamente independentes, não há como esperar o valor de retorno no corpo, e o programa não parará e espera quando eles forem abertos, caso contrário, o significado do setTimeout e do setInterval será perdido. Portanto, não faz sentido usar o retorno, portanto, o retorno de chamada só pode ser usado. O significado do retorno de chamada é notificar a função de proxy dos resultados da execução do timer para processamento oportuno.
3. As funções também são objetos
Se você deseja entender a função de retorno de chamada, primeiro deve entender claramente as regras da função. No JavaScript, as funções são estranhas, mas são realmente objetos. Para ser preciso, uma função é um objeto de função criado com o construtor function (). O objeto de função contém uma sequência que contém o código JavaScript da função. Se você foi transferido de C ou Java, isso pode parecer estranho, como o código poderia ser uma string? Mas para JavaScript, isso é bastante comum. A diferença entre dados e código é vaga.
// A função pode ser criada dessa maneira var fn = new function ("arg1", "arg2", "return arg1 * arg2;"); fn (2, 3); // 6Uma vantagem disso é que você pode passar o código para outras funções ou pode passar variáveis ou objetos regulares (porque o código é literalmente apenas um objeto).
Função de transferência como retorno de chamada
É fácil passar uma função como um parâmetro.
função fn (arg1, arg2, retorno de chamada) {var num = math.ceil (math.random () * (arg1 - arg2) + arg2); retorno de chamada (num); // Passe o resultado} fn (10, 20, função (num) {console.log ("retorno de chamada chamado! num:" + num);}); // o resultado é um número aleatório entre 10 e 20Talvez fazer isso pareça pesado e até um pouco estúpido, por que não devolver o resultado anormalmente? Mas quando você tem que usar uma função de retorno de chamada, pode não pensar assim!
Não atrapalhe
As funções tradicionais inserem os dados como parâmetros e usam as instruções de retorno para retornar valores. Em teoria, há uma declaração de retorno de retorno no final da função, que é estruturada: um ponto de entrada e um ponto de saída. Isso é mais fácil de entender. As funções estão essencialmente mapeando o processo de implementação entre entrada e saída.
No entanto, quando o processo de implementação da função for muito longo, você deve optar por aguardar a função concluir o processamento ou usar a função de retorno de chamada para executar o processamento assíncrono? Nesse caso, o uso de funções de retorno de chamada se torna crítico, como: solicitação AJAX. Se você usar uma função de retorno de chamada para processamento, o código poderá continuar executando outras tarefas sem esvaziá -lo. No desenvolvimento real, as chamadas assíncronas são frequentemente usadas em JavaScript, e é altamente recomendado aqui!
Abaixo está um exemplo mais abrangente de carregar arquivos XML usando AJAX e usar a função Call () para chamar a função de retorno de chamada no contexto do objeto solicitado.
função fn (url, retorno de chamada) {var httprequest; // Crie xhr httprequest = window.xmlhttprequest? novo xmlHttPrequest (): Window.ActiveXObject? new ActiveXObject ("Microsoft.xmlHttp"): indefinido; // Detecção funcional para ie httprequest.onReadyStatechange = function () {if (httPrequest.readystate === 4 && httPrequest.status ===t.TermEngment === 4 && httPreQuest.status ===t) {//4 JUSTEMENTE === 4 && httPrequest.status ==== 200) }}; httprequest.open ("get", url); httprequest.send ();} fn ("text.xml", function () {// Chame o function console.log (this); // saída após esta instrução}); console.log ("Isso será executado antes do retorno de chamada acima."); // Esta declaração é produz primeiroNossos pedidos de processamento assíncrono significa que, quando começamos a solicitar, dizemos a eles para ligar para nossa função quando terminarem. Em situações reais, o manipulador de eventos ONREADESTATECHANGE também deve considerar a falha da solicitação. Aqui, assumimos que o arquivo XML existe e pode ser carregado com sucesso pelo navegador. Neste exemplo, a função assíncrona é atribuída ao evento OnreadyStateChange e, portanto, não é executado imediatamente.
Finalmente, a declaração do segundo console.log é executada primeiro, porque a função de retorno de chamada não é executada até que a solicitação seja concluída.
O exemplo acima não é fácil de entender, então dê uma olhada no exemplo a seguir:
function foo () {var a = 10; retornar function () {a *= 2; retornar a; }; } var f = foo (); f (); // retorna 20.f (); // retorna 40.A função é chamada externamente e ainda pode acessar a variável a. Isso é tudo porque o escopo do JavaScript é lexical. O funcional é executado no escopo que os define (o escopo dentro do exemplo no exemplo acima), e não no escopo em que essa função é executada. Enquanto F for definido no Foo, ele pode acessar todas as variáveis definidas no Foo, mesmo que a execução do Foo tenha terminado. Porque seu escopo será salvo, mas apenas a função retornada pode acessar o escopo salvo. Retornar uma função anônima incorporada é o método mais comum para criar fechamentos.
O exposto acima é tudo sobre este artigo, espero que seja útil para todos aprenderem a programação de JavaScript.