← 返回文章列表
更新于 2026-07-28
使用 concurTask 实现并发任务的控制
在前端开发中,尤其是在处理网络请求或异步任务时,我们经常会遇到需要并发执行多个任务的场景。然而,过多的并发请求可能会导致服务器负载过高,甚至被拒绝服务。为了解决这个问题,我们可以使用并发控制技术来限制同时进行的任务数量,从而实现更加稳定和高效的异步操作。
本文介绍一个名为 concurTask 的函数,它可以帮助我们控制并发任务的执行,确保在任何时候不会超过设定的最大并发限制。
问题背景
在实际开发中,如果我们需要同时发起多个网络请求,直接并发所有请求可能会带来以下问题:
- 服务器压力过大:如果并发请求数量过多,服务器可能无法处理,导致请求失败。
- 资源竞争:浏览器对同一域名的并发请求有数量限制,过多的并发请求可能会阻塞其他重要资源的加载。
- 不必要的网络流量:如果所有请求都同时发起,即使有些请求的数据不立即需要,也会消耗网络资源。
为了解决上述问题,我们需要一种机制来控制并发请求的数量,在保证任务执行效率的同时,降低对系统的冲击。
concurTask 函数实现
concurTask 函数接收一个任务列表和一个并发限制参数,按顺序执行这些任务,确保同时执行的任务数量不超过设定的限制。
代码实现
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
| const concurTask = (tasks, limit = 1) => { return new Promise((resolve) => { const results = [] if(!tasks || !tasks.length) { resolve(results) return; }
let currentIndx = 0;
const _run = async () => { if(currentIndx >= tasks.length) return; const i = currentIndx; const task = tasks[currentIndx] currentIndx++; try { const result = await task(); results[i] = result } catch (error) { results[i] = error } finally { if(results.length === tasks.length) { resolve(results) } else { _run() } } }
const count = Math.min(tasks.length, limit) for(let i = 0; i< count; i++) { _run() } }) }
|
使用示例
假设我们有一组模拟的异步 HTTP 请求任务,我们想要以每次最多两个任务的并发来执行:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| async function http(url) { return new Promise((resolve) => { setTimeout(() => { console.log(url); resolve(url); }, 1000); }); }
concurTask([ 'http://127.0.0.1:3000/1', 'http://127.0.0.1:3000/2', 'http://127.0.0.1:3000/3' ].map(item => () => http(item)), 2);
|
在这个示例中,我们通过 concurTask 函数控制了同时执行的异步任务数量,确保每次最多只有两个任务在执行。这种方法能有效地管理资源,并降低了因并发过高导致的性能问题和竞态条件风险。
通过 concurTask 函数,开发者能够更加灵活地处理异步任务的执行顺序和并发限制,从而优化应用程序的性能和稳定性。