如何修复点击Start后加速的JavaScript定时器问题
修复JavaScript定时器重复启动加速问题
问题根源
你遇到的加速问题,核心原因是每次点击Start按钮都会调用setInterval创建一个新的定时器实例,多个定时器会同时触发计数函数,导致计数速度翻倍/多倍。原代码里的timerStarted变量只是控制计数逻辑,并没有阻止新定时器的创建。
修复方案
要解决这个问题,我们需要:
- 用变量保存定时器ID,每次启动前先清除已存在的定时器
- 优化启停状态的控制逻辑,避免重复创建定时器
修复后的完整代码
JavaScript
let seconds = 0 let decisecond = 0 let centisecond = 0 let millisecond = 0 let timerId = null // 存储定时器ID,用于后续清除 function start() { // 启动前先清除已有定时器,避免重复创建 if (timerId) { clearInterval(timerId) } // 创建新的定时器并保存ID timerId = setInterval(updateTimer, 10) } function updateTimer() { millisecond++ if (millisecond === 10) { millisecond = 0 centisecond++ } if (centisecond === 10) { centisecond = 0 decisecond++ } document.getElementById("timer").textContent = `${decisecond}.${centisecond}${millisecond}` } function pause() { // 清除定时器,暂停计数 if (timerId) { clearInterval(timerId) timerId = null } }
CSS
td { border: 1px solid black; height: 50px; width: 500px; }
HTML
<table> <td align="center"> <h1 id="timer">0.00</h1> </td> <button onclick="start()">Start</button> <button onclick="pause()">Pause</button> </table>
额外精度优化建议
如果需要更高精度的定时器,推荐使用Date对象计算时间差的方式——因为setInterval的执行间隔会受浏览器事件循环影响,存在误差:
let startTime = null; let timerId = null; function start() { if (timerId) clearInterval(timerId); // 记录启动时的时间戳 startTime = Date.now(); timerId = setInterval(() => { const elapsed = Date.now() - startTime; // 计算各单位时间 const decisecond = Math.floor(elapsed / 100); const centisecond = Math.floor((elapsed % 100) / 10); const millisecond = elapsed % 10; document.getElementById("timer").textContent = `${decisecond}.${centisecond}${millisecond}`; }, 10); } function pause() { if (timerId) { clearInterval(timerId); timerId = null; } }
内容的提问来源于stack exchange,提问作者Adam Jacobs
相关产品推荐
相关产品推荐

