JavaScript如何将for循环内调用的函数延迟到while循环指定位置执行
问题说明
业务逻辑全部位于while循环内部,循环中嵌套多层for循环用于遍历检测相邻网格内符合标记条件的单元。遍历到满足条件的相邻单元时会触发对应函数调用,需求为将所有for循环遍历过程中触发的这类函数延迟执行:仅在当次while循环内所有for循环执行完成、即将进入下一轮迭代前的指定位置统一执行,待所有延迟函数全部执行完毕后,再继续执行while循环的后续逻辑。
原有实现代码:
Cell.prototype.floodFillEach = function() { grid[orginalX][orginalY].floodFill(); while(repeat<=7){ for (var xoff = 0-x12; xoff <= 0+x12; xoff++) { for (var yoff = 0; yoff <= 0+x12; yoff++) { var i = orginalX + xoff; var j = orginalY + yoff; if (i > -1 && i < cols && j > 0 && j < rows) { var neighbour = grid[i][j]; if (neighbour.marked2) { console.log("x:"+i+" y:"+j); neighbour.floodFill(); // everytime this function is called within this while loop i need it to wait untill... } } } } // ... here. I need the functions called to wait and run here and after they are done only then proceed with the rest of this while loop x12++ repeat++ } }
解决方案
用任务队列收集遍历阶段需要触发的函数,等两层for循环全部遍历结束后再统一执行队列内的任务即可,不需要改动原有遍历判断逻辑,修改后代码如下:
Cell.prototype.floodFillEach = function() { grid[orginalX][orginalY].floodFill(); while(repeat<=7){ // 每轮循环初始化独立的待执行任务队列 const runLater = []; for (var xoff = 0-x12; xoff <= 0+x12; xoff++) { for (var yoff = 0; yoff <= 0+x12; yoff++) { var i = orginalX + xoff; var j = orginalY + yoff; if (i > -1 && i < cols && j > 0 && j < rows) { var neighbour = grid[i][j]; if (neighbour.marked2) { console.log("x:"+i+" y:"+j); // 绑定正确上下文后推入队列,不立即执行 runLater.push(neighbour.floodFill.bind(neighbour)); } } } } // for循环全部走完,按收集顺序执行所有延迟函数 runLater.forEach(fn => fn()); x12++ repeat++ } }
- 若
floodFill是异步函数,将外层函数改为async形式,队列执行部分替换为for (const fn of runLater) { await fn(); },即可保证所有异步任务执行完成后再进入后续逻辑。 - 使用
bind(neighbour)是为了固定函数执行时的this指向,避免上下文丢失导致函数运行异常。 - 每轮while循环都会重新创建空队列,不会出现不同迭代轮次的任务混淆。
- 如果单轮遍历中可能重复命中同一个neighbour单元,可在推入队列前增加去重判断,避免同一个单元的方法被重复触发。
内容的提问来源于stack exchange,提问作者Random_Person_Online
相关产品推荐
相关产品推荐

