在JavaScript的世界中,异步编程是处理并发任务的魔法棒。而async和await则是这魔法棒上的两颗璀璨宝石,它们让异步代码看起来和同步代码一样简洁明了。本文将带你深入探索async和await的7个高级用法,让你的代码更加高效、优雅。
1. 并行执行异步任务
使用Promise.all可以同时启动多个异步任务,并等待它们全部完成。
async function fetchAllData() {
const urls = ['url1', 'url2', 'url3'];
try {
const results = await Promise.all(urls.map(url => fetch(url).then(res => res.json())));
console.log(results); // 所有URL的数据
} catch (error) {
console.error('Failed to fetch data:', error);
}
}
2. 异步任务的错误处理
使用try...catch结构可以优雅地处理异步操作中的错误。
async function fetchData() {
try {
const data = await fetch('some-url').then(res => res.json());
console.log(data);
} catch (error) {
console.error('An error occurred:', error);
}
}
3. 使用async IIFE(立即执行函数表达式)
将async函数立即执行,可以在不声明变量的情况下执行异步操作。
(async () => {
try {
const data = await fetch('some-url').then(res => res.json());
console.log(data);
} catch (error) {
console.error('An error occurred:', error);
}
})();
4. 异步操作的链式调用
使用async/await可以轻松地实现异步操作的链式调用。
async function processUserData() {
const user = await getUser();
const details = await getDetails(user.id);
const profile = await getProfile(details.profileId);
console.log(profile);
}
5. 使用for...await...of循环
这个循环结构允许你在for循环中使用await,逐个处理异步迭代器。
async function processAllItems(items) {
for await (const item of items) {
await processItem(item);
}
}
6. 超时控制
使用Promise.race可以为异步操作设置超时时间。
async function fetchDataWithTimeout(url, timeout = 5000) {
const fetchPromise = fetch(url).then(res => res.json());
const timeoutPromise = new Promise((_, reject) =>
setTimeout(() => reject(new Error('Timeout')), timeout)
);
try {
return await Promise.race([fetchPromise, timeoutPromise]);
} catch (error) {
console.error('Fetch failed or timed out:', error);
}
}
7. 异常的传播
使用async/await可以在多个异步函数之间传播异常。
async function process() {
try {
const data = await fetchData();
const result = await processData(data);
await saveResult(result);
} catch (error) {
console.error('An error occurred during processing:', error);
}
}
通过这些高级用法,你可以更加灵活和强大地控制JavaScript中的异步操作,让你的代码不仅高效,而且易于理解和维护。掌握这些技巧,你将能够在异步编程的海洋中畅游无阻。