实测可得当前浏览器定时器真实压制程度,需用performance.now与setTimeout双重采样取最小间隔,前台运行、剔除异常值后中位数更可靠,后台节流下Chrome延迟升至约1000ms,Firefox仍保持10ms级精度。

直接测出当前浏览器对定时器的实际压制程度,比查文档更可靠。不同标签页状态、系统负载、甚至 macOS 与 Windows 的调度差异,都会让 setTimeout 最小间隔浮动——不能只信“4ms”这个理论值。
用 performance.now + setTimeout 双重采样法
核心思路:连续发起多个 setTimeout(0),记录每次实际触发时间戳,计算相邻两次的最小差值,即为当前环境真实延迟下限。
- 代码只需几行:
let samples = [];
for (let i = 0; i const start = performance.now();
setTimeout(() => {
samples.push(performance.now() - start);
}, 0);
}
// 稍等片刻后取 samples 中最小值(排除首尾异常) - 关键点:必须在页面前台运行;若在后台执行,Chrome/Firefox 会强制拉高到 1000ms,结果失真
- 建议重复运行 3 次,剔除最大最小值后取中位数,避免单次 GC 或调度抖动干扰
区分前台与后台节流状态
同一浏览器,前台和后台的定时器行为天差地别。需主动检测并分类评估:
- 监听 visibilitychange 事件,在 document.hidden 为 true 时立即切换测试逻辑
- 后台测试改用:setTimeout(() => {}, 100) → 实际延迟若稳定在 990–1010ms,基本可判定进入后台节流模式
- Firefox 后台仍允许 performance.now 单调递增,可结合它验证是否真被节流,还是单纯主线程空闲
跨浏览器横向对比参考值(实测典型场景)
以下为 2026 年主流浏览器在标准配置下的常见阈值,仅作锚点参考,务必以实测为准:
- Chrome(前台):通常 0.5–2ms(依赖硬件与系统负载),但受 event loop 阻塞影响明显
- Firefox(前台):多数 1–3ms,后台仍保持 ~10ms 级别精度(优于 Chrome 后台)
- Safari(macOS):前台约 4–10ms;iOS Safari 常卡在 10–16ms,且 performance.now 分辨率更低
- Edge(Chromium 内核):行为与 Chrome 高度一致,前台延迟基本相同
规避假阳性:排除主线程阻塞干扰
如果测出延迟突然变大(如从 2ms 跳到 20ms),未必是浏览器限速,更可能是当前页面正执行长任务:
- 用 requestIdleCallback 包裹测试逻辑,确保在主线程空闲时运行
- 加一个简单防护:先执行 let t = performance.now(); while (performance.now() - t
- 若使用 Web Worker 运行该检测脚本,所得结果更能反映浏览器底层调度能力,不受主线程 JS 执行影响


















