Problems/Requirements:

  • Anyway, the interviewer has asked us to do the basicsPromise, includingpromiseThe callbackresolveandrejectAnd those returned after processing the state.thenMethod, so next, we will continue to implementPromiseThe method of processing multiple asynchronous requests/processing after completion, output againall

Solution/Handling procedure

Analysis process:

  • The parameter of the all method is an array. In this array, it is supposed to store the data of the promise type, but (as we all know, not all cases in this world are ideal, so, need to be processed, but, First of all, let’s just say that if is the norm, the data in the array is of type promise.

The preliminary implementation

  • First basic processing, according to the passed parameters, traversal, return data. And see what the problem is
   // The basic implementation and method of promise are not posted here, you can check the series 1 article, here are the main points
   all(promises) {
       // All can also be chained, so we need to return a promise like then
       return new Promise((resolve, reject) = > {            
           let res = []     // An array to store all the results returned after processing
           const length = promises.length // The array length of the argument passed in
           promise.forEach((promise, index) = >{
           // Iterate over each promise object in the array, calling its then method to retrieve resolve or Reject data
               promise.then(result= > {
               // handle a push
                   res.push(result)
               // Resolve returns when the res result array is the same length as the passed argument
               if(res.length === promiseLength) resolve(res)
                   }).catch(e= > reject(e))
               })
           })
       
       })
   }
Copy the code
  • ForEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach forEach So, here’s a type judgment.
 // The basic implementation and method of promise are not posted here, you can check the series 1 article, here are the main points
 all(promises) {
     // All can also be chained, so we need to return a promise like then
     return new Promise((resolve, reject) = >{+if(!Array.isArray(promises)){
+           // pit 1: Reject the data type of the passed parameter. If it is not an array type, reject throws a message
+               return reject('The argument passed must be in array format! ') +}let res = []     // An array to store all the results returned after processing
         const length = promises.length // The array length of the argument passed in
         promise.forEach((promise, index) = >{
         // Iterate over each promise object in the array, calling its then method to retrieve resolve or Reject data
             promise.then(result= > {
             // handle a push
                 res.push(result)
             // Resolve returns when the res result array is the same length as the passed argument
             if(res.length === promiseLength) resolve(res)
                 }).catch(e= > reject(e))
             })
         })
     })
 }
Copy the code
  • At this point, the parameter type passed in is fine, but! The forEach loop iterates through each object, calling the. Then method directly, and if the data being iterated is not a promise object from the suture specification, then an error will be reported. If it is not a Promise object, return the current iterated object. No then operation is performed, but! There’s actually a good trick here. Take a look below.
        promise.forEach((promise, index) = >{
            // If a promise is a promise, it can be a number or something else.
            // The Promise static resolve method is now a Promise type, regardless of whether it was originally a Promise
            let res = []
            const promiseLength= promises.length
            Promise.resolve(promise).then(result= > {
                // Pit 3: There should be a counter here, because promise.all is returned sequentially, not sequentially with I
                // handle a push
               res.push(result)
                // Resolve returns when the res result array is the same length as the passed argument
                if(res.length === promiseLength) resolve(res)
              }).catch(e= > reject(e))

Copy the code
  • That may someone will say, so should have no what problem! The parameter passed in determines the type, and the current object type traversed is handled. Yes, the data type passed in is now handled. Do you notice anything about the output? The order of the results returned by the all method corresponds to the order of the parameters passed in. The order of the results returned by the all method corresponds to the order of the parameters passed in. Here’s a look:
     promise.forEach((promise, index) = >{
            // If a promise is a promise, it can be a number or something else.
            // The Promise static resolve method is now a Promise type, regardless of whether it was originally a Promise
            let res= []
            const promiseLength= promises.length
            Promise.resolve(promise).then(result= > {
                // Pit 3: There should be a counter here, because promise.all is returned sequentially, not sequentially with I
+                res[index] = result // Use the subscript of the current traversal to store the output in the same order
                // handle a push
-               res.push(result)  // Not push directly, because asynchrony does not guarantee that the results will be returned in order
                // Resolve returns when the res result array is the same length as the passed argument
                if(res.length === promiseLength) resolve(res)
              }).catch(e= > reject(e))

Copy the code
  • Here, solved the output order problem, there should be no problem! The interviewer asks, “Have you considered what would happen to your program if the last index was printed first?” “, here look there take a look, heart OS: “no problem ah”, “really no problem? If the last one is the first one, then the length of the array is the same as the length of the argument passed in.
    promise.forEach((promise, index) = >{
            // If a promise is a promise, it can be a number or something else.
            // The Promise static resolve method is now a Promise type, regardless of whether it was originally a Promise
            let res= []
+           let count = 0 // It is used to record how much data is processed
            const promiseLength= promises.length
            Promise.resolve(promise).then(result= > {
                // Pit 3: There should be a counter here, because promise.all is returned sequentially, not sequentially with I
                res[index] = result // Use the subscript of the current traversal to store the output in the same order
+               count++  // Process one counter plus one
-                // Resolve returns when the res result array is the same length as the passed argument
-                if(res.length === promiseLength) resolve(res)
+                if(count === promiseLength) resolve(res) // This parameter is returned only when the number of processes is in the same format as the parameter
             }).catch(e= > reject(e))

Copy the code
  • At this point, the promise.all methods are complete. In fact, usually feel very convenient to use, but also need to know why, learning to learn the excellent code crystallization of predecessors, even for their own a little bit of 🤏 promotion is also good.

  • Finally, to the all method of all implementation and a few points to note ⚠️:

     // The basic implementation and method of promise are not posted here, you can check the series 1 article, here are the main points
     all(promises) {
         // All can also be chained, so we need to return a promise like then
         return new Promise((resolve, reject) = > {
             if(!Array.isArray(promises)){
             // pit 1: Reject the data type of the passed parameter. If it is not an array type, reject throws a message
                 return reject('The argument passed must be in array format! ')}let res = []     // An array to store all the results returned after processing
             let count = 0    // The number of requests/data that have been processed
             const length = promises.length // The array length of the argument passed in
             promise.forEach((promise, index) = >{
             // Pit 2: This is supposed to determine if a promise is a promise, because it could be a number or something else.
             // The Promise static resolve method is now a Promise type, regardless of whether it was originally a Promise
             Promise.resolve(promise).then(result= > {
                 // Pit 3: There should be a counter here, because promise.all is returned sequentially, not sequentially with I
                 count ++
                 res[index] = result
                 // pit 4: there is an error in using length, because if there is a seventh array in js, the length is still 7(undefined).
                 if(count === promiseLength) resolve(res)
                     }).catch(e= > reject(e))
                 })
             })
         
         })
     }
    Copy the code

The basic implementation of Promise and the.then methodCheck out the interview handwritten Promise series I

Front-end whiteness, so far, we have implemented reslove, Reject, then, all methods, race method will output front-end whiteness in the next article, there are errors and improper place, forget you big god pointed out, if you feel the small brother code word is not easy, trouble to 👍, thank you!