How to use async and await correctly in JS loops

How to use async and await correctly in JS loops

Overview (Loop Mode - Common)

  • for
  • map
  • forEach
  • filter

Declare array and asynchronous method to iterate

Declare an array: ⬇️

const skills = ['js', 'vue', 'node', 'react']

Declare another promise asynchronous code: ⬇️

function getSkillPromise (value) {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve(value)
    }, 1000)
  })
}

Use in for loop

Since the for loop is not a function, and async and await need to be used in functions, we need to wrap a layer of function inside the for loop.

async function test () {
  for (let i = 0; i < skills.length; i++) {
    const skill = skills[i]
    const res = await getSkillPromise(skill)
    console.log(res)
  }
}

test() // call 

When using await, you want JavaScript to pause execution until the awaited promise returns a result. The above result means that if there is asynchronous code in the for loop, you can wait until the asynchronous code in the for loop is completely run before executing the code after the for loop.

But it cannot handle callback loops, such as forEach, map, filter, etc. The following is a detailed analysis.

Use in map

When using await in map, the return value of map is always a promise array, because asynchronous functions always return promises.

async function test () {
  console.log('start')
  const res = skills.map(async item => {
    return await getSkillPromise(item)
  })
  console.log(res)
  console.log('end')
}

test()

Result: always an array of promises

start
[
  Promise { <pending> },
  Promise { <pending> },
  Promise { <pending> },
  Promise { <pending> }
]
end

If you want to wait until the promise is fulfilled, you can use promise.all() to handle it.

async function test () {
  console.log('start')
  const res = skills.map(async item => {
    return await getSkillPromise(item)
  })
  const resPromise = await Promise.all(res)
  console.log(resPromise)
  console.log('end')
}

test()

// Result start
[ 'js', 'vue', 'node', 'react' ]
end

Use in forEach

First, the code and results

async function test () {
  console.log('start')
  skills.forEach(async item => {
    const res = await getSkillPromise(item)
    console.log(res)
  })
  console.log('end')
}

test()

Expected Results

'Start'

'js'

'vue'

'node'

'react'

'End'

The actual result is that console.log('end') is executed before the forEach loop waits for the asynchronous result to be returned.

'Start'

'End'

'js'

'vue'

'node'

'react'

forEach in JavaScript does not support promise awareness, nor does it support async and await, so you cannot use await in forEach.

Use in filter

Use filter to filter item as vue or react option

Use filter normally:

async function test () {
  console.log('start')
  const res = skills.filter(item => {
    return ['vue', 'react'].includes(item)
  })
  console.log(res)
  console.log('end')
}

test() // call // result start
[ 'vue', 'react' ]
end

After using await:

async function test () {
  console.log('start')
  const res = skills.filter(async item => {
    const skill = await getSkillPromise(item)
    return ['vue', 'react'].includes(item)
  })
  console.log(res)
  console.log('end')
}

test()

Expected results:

start

[ 'vue', 'react' ]

end

Actual Result:

[ 'js', 'vue', 'node', 'react' ]

end

Conclusion: Because the promise returned by the asynchronous function getSkillPromise is always true, all options pass the filter.

Attached with usage summary

  1. If you want to execute await calls serially, use a for loop (or any loop without callbacks).
  2. Never use await with forEach, use a for loop (or any loop without callbacks) instead.
  3. Do not use await in filter and reduce. If necessary, use map to further process the result, and then use filter and reduce to process the result.

Conclusion: Due to the large form extraction component encountered in the work, asynchronous verification encountered this problem. Later, after consulting the data, the result was summarized

Summarize

This is the end of this article about the correct use of async and await in JS loops. For more relevant content about the use of async and await in JS loops, please search for previous articles on 123WORDPRESS.COM or continue to browse the related articles below. I hope you will support 123WORDPRESS.COM in the future!

You may also be interested in:
  • How to use async await elegantly in JS
  • A more elegant error handling method in JavaScript async await
  • A simple and in-depth study of async and await in JavaScript
  • The use and methods of async and await in JavaScript
  • Detailed explanation of JavaScript Promise and Async/Await
  • How to use async and await in JS

<<:  Basic learning tutorial of table tag in HTML

>>:  Introduction to user management under Linux system

Recommend

Installation of CUDA10.0 and problems in Ubuntu

The correspondence between tensorflow version and...

Detailed explanation of the principle of creating tomcat in Eclipse

When creating a tomcat server on a local eclipse,...

Nginx installation detailed tutorial

1. Brief Introduction of Nginx Nginx is a free, o...

WeChat applet implements the snake game

This article shares the specific code of the WeCh...

Detailed example of MySQL subquery

Subquery Classification Classification by returne...

Css3 realizes seamless scrolling and anti-shake

question The seamless scrolling of pictures and t...

Summary of common docker commands

Docker installation 1. Requirements: Linux kernel...

30 excellent examples of color matching in web design

Today, this article has collected 30 excellent cas...

Analysis of the principle of using PDO to prevent SQL injection

Preface This article uses pdo's preprocessing...

How to deploy a simple c/c++ program using docker

1. First, create a hello-world.cpp file The progr...

A brief introduction to the usage of decimal type in MySQL

The floating-point types supported in MySQL are F...

Detailed code for adding electron to the vue project

1. Add in package.json "main": "el...