async / await really it is not as simple as you think

First on the code

Common code

function getData(data, time) {
                return new Promise(function (resolve, reject) {
                    setTimeout(function () {
                        resolve(data);
                    }, time)
                })
            }
            let results = [];
            let startTime = new Date();
            laucher();

A code segment

   async function laucher() {
                let dataA = await getData('a', 2000);
                results.push(`${dataA}在${new Date() - startTime}毫秒放入`);
                let dataB = await getData('b', 3000);
                results.push(`${dataB}在${new Date() - startTime}毫秒放入`);
                let dataC = await getData('c', 1000);
                results.push(`${dataC}在${new Date() - startTime}毫秒放入`);
                console.log(results, `输出时间${new Date() - startTime}毫秒`);
            }
            

Export

["a在2002毫秒放入", "b在5004毫秒放入", "c在6006毫秒放入"] "输出时间6006毫秒"

Two code segments

 async function laucher() {
              let dataAPromise = getData('a', 2000);
              let dataBPromise = getData('b', 3000);
              let dataCPromise = getData('c', 1000);
              let promises = [dataAPromise, dataBPromise, dataCPromise];
              results = await Promise.all(promises);
              console.log(results, `输出时间${new Date() - startTime}毫秒`);
            }

Export

["a", "b", "c"] "输出时间3006毫秒"

Snippet three

           async function laucher() {
              let dataAPromise = getData('a', 2000);
              let dataBPromise = getData('b', 3000);
              let dataCPromise = getData('c', 1000);
              dataA = await dataAPromise;
              results.push(`${dataA}在${new Date() - startTime}毫秒放入`);
              dataB = await dataBPromise;
              results.push(`${dataB}在${new Date() - startTime}毫秒放入`);
              dataC = await dataCPromise;
              results.push(`${dataC}在${new Date() - startTime}毫秒放入`);
              console.log(results, `输出时间${new Date() - startTime}毫秒`);
            }

Export

["a在2003毫秒放入", "b在3001毫秒放入", "c在3001毫秒放入"] "输出时间3002毫秒"

Snippet four

     async function laucher() {
              let dataAPromise = getData('a', 2000);
              let dataBPromise = getData('b', 3000);
              let dataCPromise = getData('c', 1000);
              (async () => {
                dataA = await dataAPromise;
                results.push(`${dataA}在${new Date() - startTime}毫秒放入`);
              })();
              (async () => {
                dataB = await dataBPromise;
                results.push(`${dataB}在${new Date() - startTime}毫秒放入`);
                console.log(results, `输出时间${new Date() - startTime}毫秒`);//results放在最后返回的请求中
              })();
              (async () => {
                dataC = await dataCPromise;
                results.push(`${dataC}在${new Date() - startTime}毫秒放入`);
              })();
            }

Export

["c在1002毫秒放入", "a在2002毫秒放入", "b在3003毫秒放入"] "输出时间3003毫秒"

to sum up

SetTimeout using simulated three asynchronous request, 2000,3000,1000 ms after each return to 'a', 'b', 'c',
the first method is well understood that, step by step is performed, this method is suitable for parameter-dependent request a request to return the value of the case, where this relationship does not exist, that is, the efficiency of this approach here is relatively low.

The second method outset, launched three requests and waiting to acquire data after 3 requests arrive.

A third method is also a start request initiated 3, and sequentially executed in the request arrives, because a request arrival time is 2 seconds, a request arrives, the result of a push Results, then down implementation, b request is 3 seconds, one second request b a request arrives later, after one second is another result of the push-b results ,, c is 1 second request, this time c already arrived at the end of this round cycle immediately the push c. a return of the requested data can be operated for 2 seconds, this method can process data faster than the second method. If the request is in descending order of time, then the effect is the same and the second method, there is generally no case when there are multiple requests.

The fourth difference method and the third method is the first to reach the request of the fastest into the result set, that is, I do not line up waiting to be processed, which returns the data to me which data is processed first, if the request to return the data to c take a long time to process, I will be able to begin processing a second later, but after the third method I have three seconds to get started. I can see the results on the output of the function b request arrives, because the results after the last request in order to reach full output difference, and the three methods is to get the result of the operation is asynchronous, this is very important, and also method three biggest difference, from a function performed by wrapping the outer layer, can be prevented await operation right external laucher bounce, thereby initiating three concurrent operation results acquired. We may be in doubt if I do not know which request finally arrives, how to obtain the final value of the results, this situation can bread out a Promise.all, can look carefully distinguish the following two functions

  async function laucher() {
              let dataAPromise = getData('a', 2000);
              let dataBPromise = getData('b', 3000);
              let dataCPromise = getData('c', 1000);
              let promises = [dataAPromise, dataBPromise, dataCPromise];
              results = await Promise.all(promises);
              console.log(results, `输出时间${new Date() - startTime}毫秒`);
            }

Export

["a", "b", "c"] "输出时间3003毫秒"
    async function laucher() {
              let dataAPromise = getData('a', 2000);
              let dataBPromise = getData('b', 3000);
              let dataCPromise = getData('c', 1000);
              let promises = [dataAPromise, dataBPromise, dataCPromise];
              results = await Promise.all(promises.map(async function (promise) {
                let data = await promise;
                console.log(`${data}在${new Date() - startTime}毫秒输出`);
                //这里可以提前处理数据
                return data
              }));
              console.log(results);
            }

Export

c在1002毫秒输出
a在2003毫秒输出
b在3003毫秒输出
["a", "b", "c"] "输出时间3004毫秒"

If the request does not exist between the secondary relationship, and reaches to the request to perform some operation, then press for efficiency
Method 4> Method 3> Method 2> Method 1
each of these methods of loading a strategy to use a scene to illustrate, the page is loaded components (assuming that the number of components is 3) to the background
execution flow:

Method a: request initiating module 1 -> assembly data arrival render component 1 -> initiation request assembly 2 -> assembly 2 data arrival render component 2 -> initiating component requests 3 -> assembly 3 data arrival rendered component 3

Method two: simultaneously initiating a request assembly 1,2,3 -> After reaching the data components are 1,2,3 1,2,3 render component

Method three: simultaneously initiating a request assembly 1,2,3 -> assembly 1 reaches render component data 1 -> After assembly 2 data arrives render component 2 -> 3 component data arrival render component 3

Method four: simultaneously initiating a request assembly 1,2,3 -> component data arriving fastest arrival render component arriving fastest -> the second component data reaches faster render component arrives after the arrival of the second fast -> most slow component data arrives after reaching render the slowest component of arrival

For the above scenario can be seen FOUR allows the fastest rendering our page content

At last

It can be seen despite the introduction of async / await, you can make your code very concise, but async / await execution process itself is very complex, the following code you can guess the output (add one point: Some articles will point out forEach function can not be placed asynchronous operation, this conclusion is wrong, if it is really secondary to the relationship is inappropriate to forEach, but not that they can not put an asynchronous operation, but this operation can improve the efficiency of access to data)

 [1, 2].forEach(async function (value) {
              console.log(value);
              await console.log('a');
              console.log('c');
              await console.log('d');
              console.log('e');
            })
            console.log(3);

Guess you like

Origin www.cnblogs.com/homehtml/p/12031962.html