使用setTimeout调用person_A和person_B时输出格式异常排查
JavaScript setTimeout执行异常分析与修正
问题背景
我们需要通过三个步骤调用两个函数,用setTimeout()控制执行延迟:
- 步骤1:先执行
person_A(),再执行person_B() - 步骤2:先执行
person_B(),延迟3秒后执行person_A() - 步骤3:执行
person_A(),延迟3秒后在其内部调用person_B()
预期输出:
-----------> STEP 1 <---------------- Hi Am person_A() Hi Am person_B() -----------> STEP 2 <---------------- Hi Am person_B() Hi Am person_A() -----------> STEP 3 <---------------- Hi Am person_A() Hi Am person_B()
实际错误输出:
-----------> STEP 1 <---------------- Hi Am person_A() Hi Am person_B() -----------> STEP 2 <---------------- Hi Am person_B() -----------> STEP 3 <---------------- Hi Am person_A() Hi Am person_B() Hi Am person_A()
错误原因
异步任务时序冲突:
步骤2中person_A()的setTimeout是异步任务,会进入浏览器事件队列等待3秒后执行,但代码不会等待它完成,会直接继续执行步骤3的逻辑。这导致步骤2的person_A()输出被延迟到步骤3之后,看起来像是步骤2缺失了输出,实际是和步骤3的输出混在了一起。函数变量重复覆盖:
三个步骤反复给同一个person_A和person_B变量赋值新函数,步骤2和步骤3的异步任务会先后触发,最终导致额外的person_A()输出。
修正方案
核心是避免重复覆盖函数变量,同时控制步骤间的异步时序:
/* 步骤1:先执行person_A,再执行person_B */ console.log("\n-----------> STEP 1 <----------------\n"); const personA1 = () => { console.log(" Hi Am person_A() "); }; const personB1 = () => { console.log(" Hi Am person_B() "); }; personA1(); personB1(); /* 步骤2:先执行person_B,延迟3秒后执行person_A */ console.log("\n-----------> STEP 2 <----------------\n"); const personA2 = () => { setTimeout(() => { console.log(" Hi Am person_A() "); }, 3000); }; const personB2 = () => { console.log(" Hi Am person_B() "); }; personB2(); personA2(); /* 步骤3:等待步骤2完成后,执行person_A并延迟3秒调用person_B */ setTimeout(() => { console.log("\n-----------> STEP 3 <----------------\n"); const personA3 = () => { setTimeout(() => { console.log(" Hi Am person_A() "); personB3(); }, 3000); }; const personB3 = () => { console.log(" Hi Am person_B() "); }; personA3(); }, 3500);
修正说明
- 独立函数命名:每个步骤使用不同的函数变量名(如
personA1、personA2),彻底避免变量覆盖导致的逻辑混乱。 - 时序控制:用
setTimeout包裹步骤3的代码,等待步骤2的3秒延迟完成后再执行,确保各步骤的输出不会互相穿插。 - 简化代码:将
setTimeout内的匿名函数替换为箭头函数,提升代码可读性。
修正后即可得到符合预期的输出结果。
内容的提问来源于stack exchange,提问作者Mohemmad
相关产品推荐
相关产品推荐

