js est la meilleure façon d'effectuer une nouvelle opération après deux opérations asynchrones AJax
世界只因有你
世界只因有你 2017-07-05 10:54:02
0
11
1671

J'ai rencontré une question d'entretien aujourd'hui, c'est-à-dire que s'il y a deux opérations ajax asynchrones sur la page, parce que je ne suis pas sûr de l'ordre d'exécution de ces deux opérations asynchrones, comment puis-je exécuter une nouvelle opération une fois les deux opérations exécutées ? Meilleure Quelle est la méthode ?

J'ai répondu à la première méthode à ce moment-là : imbriquer deux ajax et effectuer de nouvelles opérations dans la fonction de retour du deuxième ajax. Réponse de l'intervieweur : Cette méthode est trop boiteuse.

J'ai donc réfléchi à la deuxième réponse : surveiller les variables locales via le timer setTimeout et m'assurer que les deux opérations asynchrones sont terminées avant d'effectuer une nouvelle opération. Réponse de l'enquêteur : Les performances de cette méthode ne sont pas bonnes. Pouvez-vous penser à une méthode simple et plus raisonnable ?

Je n'y avais pas pensé à l'époque
Alors j'ai posé cette question pour savoir quelle est la meilleure solution ? Bienvenue pour discuter et donner des conseils

世界只因有你
世界只因有你

répondre à tous(11)
学习ing

1. La promesse enveloppe les opérations ajax asynchrones,
2. Définir la fonction asynchrone,
3. Utilisez wait pour attendre la fin de l'acquisition asynchrone des données promises. Cette méthode est simple et efficace. ci-dessous. Je suis trop paresseux pour l'utiliser. Une fois qu'ajax a obtenu les données, utilisez la fonction settimeout pour simuler l'obtention de données. Cette fonction est asynchrone et a le même principe et le même effet.

//模拟ajax异步操作1
function ajax1() {
    const p = new Promise((resolve, reject) => {
        setTimeout(function() {
            resolve('ajax 1 has be loaded!')
        }, 1000)
    })
    return p

}
//模拟ajax异步操作2
function ajax2() {
    const p = new Promise((resolve, reject) => {
        setTimeout(function() {
            resolve('ajax 2 has be loaded!')
        }, 2000)
    })
    return p
}
//等待两个ajax异步操作执行完了后执行的方法
const myFunction = async function() {
    const x = await ajax1()
    const y = await ajax2()
        //等待两个异步ajax请求同时执行完毕后打印出数据
    console.log(x, y)
}
myFunction()
漂亮男人

http://api.jquery.com/jQuery....

为情所困

La méthode native prête à l'emploi actuelle dans l'environnement du navigateur est Promise.all.

Prenons l'exemple de l'appel de ma bibliothèque de cartes Sinomap Demo Pour charger une carte sur cette page, plusieurs demandes doivent être lancées en même temps mais l'ordre de retour ne peut pas être garanti :

  1. Données de terrain en Chine

  2. Données JSON de chaque province

  3. Lorsque plusieurs graphiques sont superposés, plusieurs données JSON dans plusieurs graphiques doivent être renvoyées via différentes interfaces de données...

La solution est directement dans le déballé http://sinomap.ewind.us/demo/demo.js, exemple :

// 封装地形 GeoJSON 数据接口
// 将每个数据接口封装为一个返回 Promise 的函数
function getArea () {
  return new Promise((resolve, reject) => {
    fetch('./resources/china.json').then(resp =>
      resp.json().then(china => resolve(china))
    )
  })
}

// 封装分色地图数据接口
function getPopulation () {
  return new Promise((resolve, reject) => {
    fetch('./resources/china-population.json').then(resp =>
      resp.json().then(data => resolve(data))
    )
  })
}

// 封装城市数据接口
function getCity () {
  return new Promise((resolve, reject) => {
    fetch('./resources/city.json').then(resp =>
      resp.json().then(data => resolve(data))
    )
  })
}

// 使用 Promise.all 以在三个数据接口均异步成功后,执行回调逻辑
Promise.all([getArea(), getPopulation(), getCity()]).then(values => {
  // 依次从返回的数据接口数组中获取不同接口数据
  let china = values[0]
  let population = values[1]
  let city = values[2]
  // 使用数据
  doWithData(china, population, city)
})

De cette façon, Promise réalise non seulement le découplage de la logique de rappel, mais réalise également un contrôle de processus asynchrone de base.

小葫芦

Je viens de voir la méthode when de jquery, alors j'en ai réécrit une pour vous. Ce n'est peut-être pas aussi bon que jquery, mais au moins cela peut obtenir l'effet. Vous pouvez directement entrer le code suivant dans la console pour essayer. aller écrire. Cela m'a pris une demi-heure. .

function ajax(callback){
    callback = callback || function(){};
    var xhr = new XMLHttpRequest();
    xhr.open("get","");
    xhr.onload = function(res){ callback(res) };
    xhr.send(null); 
}

var when = (function(){
    var i = 0,
        len = 0,
        data = [];
    return function(array,callback){
        callback = callback || function(){};
       len = len || array.length;
        var fn = array.shift();
       
       fn(function(res){
            i++;
            data.push(res);
            if(i < len){
                when(array,callback);
            } else {
                callback(data);
            } 
       });   
    };
})();

when([ajax,ajax],function(data){
    console.log(data);
});
给我你的怀抱

Demandez si je peux utiliser jQ. Si oui, dites simplement :

$.when($.ajax("page1"), $.ajax("page2")).done(function(){});

Au fait, voici la référence de la documentation de $.when

为情所困

Je pense que c'est la méthode de Promise, tout ou quelque chose comme ça

学习ing

Votre question est la suivante : il y a trois choses a, b, c. c doit être exécuté une fois a et b terminés.

Il existe de nombreuses méthodes : comme la méthode de nidification que vous avez évoquée, et la méthode de surveillance violente

J'ai déjà réfléchi à cette question et voici ma réponse.

Émetteur asynchrone

Comment effectuer des opérations asynchrones à l'aide du stockage sur baie

Notez que les fonctions à l'intérieur ont toutes un paramètre commit , qui est une fonction utilisée pour renvoyer une valeur. Lorsque ajax réussit, transmettez simplement la valeur de retour

// 两个异步操作  
var todos = [
    function getUser(commit){ 
        setTimeout(() => {
            commit({  // 这里是异步结束的时候 利用 commit 把值回传 
                name: 'eczn',
                age: 20
            }, 233); 
        }); 
    },
    function getLoc(commit){
        setTimeout(() => {
            commit({
                area: '某个地方'
            });
        }, 333); 
    }
]; 

Écrire un lanceur

Les processeurs sont des données comme des tâches. cb est le rappel final.

function launcher(processors, cb){
    var o = {}; 
    var count = 0; 
    if (processors.length === 0) cb(o); 

    processors.forEach((func, idx) => {
        func(function commit(asyncVal){ // 这就是commit函数 
            // 把 asyncVal 的所有属性合并到 o 上 
            // ( 利用 Object.keys 获取对象全部属性名 )
            Object.keys(asyncVal).forEach(key => {
                o[key] = asyncVal[key]; 
            }); 
            
            // 计数器自加 
            count++; 
            // 如果发射器全部发射完毕则调用回调函数 cb 并把 o 作为参数传递
            if (count === processors.length) cb(o); 
        }); 
    }); 
}

Concurrent eux

Exécuter un émetteur asynchrone et fournir 最终回调

launcher(todos, function(whereEczn){
    // todos 里面存放的异步操作的值由 commit 回调返回
    // 全部回调跑完的时候 就会执行当前这段函数 并把期望值返回
    console.log(whereEczn); 

    // 按顺序输出
    ['name', 'area'].forEach(key => {
        console.log(`${key}: ${whereEczn[key]}`); 
    }); 
});

Lien

https://eczn.coding.me/blog/%...

世界只因有你

Vous pouvez définir une variable a=0 et définir a++ dans le rappel une fois la requête ajax réussie
Ensuite, jugez a==2 dans les deux rappels et exécutez la fonction d'opération

 ;
Peter_Zhu

Définissez deux indicateurs, puis deux ajax appellent le même rappel. Dans ce rappel, il est jugé que les deux indicateurs sont vrais avant que les opérations suivantes ne soient effectuées.

漂亮男人

Écrivez ajax dans un autre ajax et exécutez-le dans le rappel

Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal