在 JavaScript 中,可以使用 Performance API 中的 PerformanceObserver 来监视和统计长任务(Long Task)。长任务是指那些执行时间超过 50 毫秒的任务,这些任务可能会阻塞主线程,影响页面的交互性和流畅性。
console.time()
和console.timeEnd()
JavaScript 提供了 console.time()
和 console.timeEnd()
方法来测量代码块的执行时间。
console.time('longTask');
// 你的长任务代码
for (let i = 0; i < 1e7; i++) {
// ...
}
console.timeEnd('longTask');
简单粗暴。这种方法仅适用于手动测量,并且每次都需要手动添加代码。
浏览器的 Performance API 提供了高精度的时间戳,可以用来测量长任务的时间和执行次数。performanceentry
事件,可以监测到长任务并获取相关信息。
// 创建一个性能观察者实例来订阅长任务
let observer = new PerformanceObserver((list) => {
for (const entry of list.getEntries()) {
console.log("Long Task detected:");
console.log(`Task Start Time: ${entry.startTime}, Duration: ${entry.duration}`);
}
});
// 开始观察长任务
observer.observe({ entryTypes: ["longtask"] });
// 启动长任务统计数据的变量
let longTaskCount = 0;
let totalLongTaskTime = 0;
// 更新之前的性能观察者实例,以增加统计逻辑
observer = new PerformanceObserver((list) => {
list.getEntries().forEach((entry) => {
longTaskCount++; // 统计长任务次数
totalLongTaskTime += entry.duration; // 累加长任务总耗时
// 可以在这里添加其他逻辑,比如记录长任务发生的具体时间等
});
});
// 再次开始观察长任务
observer.observe({ entryTypes: ["longtask"] });
在上面的代码中,创建了一个PerformanceObserver对象来订阅长任务。每当检测到长任务时,它会向回调函数传递一个包含长任务性能条目的列表。在这个回调中,可以统计长任务的次数和总耗时。
以下是如何在实际使用中停止观察和获取当前的统计数据:
// 停止观察能力
observer.disconnect();
// 统计数据输出
console.log(`Total number of long tasks: ${longTaskCount}`);
console.log(`Total duration of all long tasks: ${totalLongTaskTime}ms`);
通过AOP,可以在函数执行前后添加额外的逻辑,而无需修改原函数。这可以通过使用像 Function.prototype.before
和 Function.prototype.after
这样的自定义方法(虽然这些方法在原生JavaScript中不存在,但可以通过原型扩展实现)或使用专门的库(如 lodash 的 _.wrap()
)来实现。
使用 Web Workers 统计长任务时间和执行次数的基本思路是将性能监测的逻辑放入 Worker 中,从而使得监测本身不会成为主线程的负担。Worker 可以周期性地向主线程报告长任务的信息,而主线程则可以更新用户界面或记录这些数据。
// worker.js
self.addEventListener('message', function(e) {
if (e.data === 'start') {
// 开始监测长任务
self.performance.observe({ entryTypes: ['longtask'] });
}
});
self.performance.addEventListener('longtask', function(entry) {
// 当检测到长任务时,发送消息到主线程
self.postMessage({
duration: entry.duration,
startTime: entry.startTime
});
});
// 主线程
const worker = new Worker('worker.js');
// 启动 Worker 监测长任务
worker.postMessage('start');
let longTasksCount = 0;
let totalDuration = 0;
worker.onmessage = function(e) {
// 更新长任务统计信息
longTasksCount++;
totalDuration += e.data.duration;
// 可以在这里更新用户界面或记录数据
console.log(`长任务持续时间: ${e.data.duration}ms, 开始时间:${e.data.startTime}`);
console.log(`长任务总数: ${longTasksCount}, 总持续时间:${totalDuration}ms`);
};
// 如果需要,可以停止监测
// worker.postMessage('stop');
在这个例子中,Worker 使用了 performance.observe 方法来监测长任务。每当检测到一个长任务时,它就会向主线程发送一条消息,其中包含长任务的持续时间和开始时间。主线程接收到这些消息后,可以更新长任务的统计信息,并执行相应的操作,比如记录数据或更新用户界面
可以考虑使用像 Lighthouse、Chrome DevTools 的 Performance Tab 或其他前端性能监控工具来自动识别和测量长任务。这些工具通常提供了更详细的性能数据和分析。
如果需要将这些统计数据发送到服务器进行分析或存储,可以使用 AJAX、Fetch API 或其他方法将这些数据发送到后端 API。另外,通过定期检查时间戳差值来检测长任务。例如,可以在requestAnimationFrame回调中记录时间戳,并检查与上次回调的时间差是否超过50毫秒。
最后
还没有使用过我们刷题网站(https://fe.ecool.fun/)或者前端面试题宝典的同学,如果近期准备或者正在找工作,千万不要错过,题库主打无广告和更新快哦~。
老规矩,也给我们团队的辅导服务打个广告。