passive的作用和原理

article/2025/10/26 5:58:00

passived到底有什么用?

passived主要用于优化浏览器页面滚动的性能,让页面滚动更顺滑~~BetterScroll:可能是目前最好用的移动端滚动插件

passived产生的历史时间线

addEventListener():大家都是认识的,为dom添加触发事件,故事就从这里开始。
在早期addEventListener是这样的:


addEventListener(type, listener, useCapture)

useCapture:是否允许事件捕捉,但是很少会传true,然后就变成可选项了:


addEventListener(type, listener[, useCapture ])

到现在就变成了这个样子:


addEventListener(type, listener, {capture: false, //捕获passive: false, once: false    //只触发一次
})

我们的主角passive就出现了

passive为什么能优化页面的滚动性能?

简述chrome的线程化渲染框架

chrome的线程化渲染框架的两个线程:

  • 内核线程(Main/Render Thread):负责DOM树构建、元素的布局、图层绘制记录部分(main-thread side)、JavaScript的执行
  • 合成线程(Compositor Thread):图层绘制实现部分(impl-side)、图层图像合成


上图可知,页面Frame#1在内核线程中完成js执行、布局和绘制后,经过一个周期合成线程去执行Frame#1页面图像的合成。

用户输入事件分类:

  • 在内核线程处理的事件
  • 直接由合成线程处理的事件

那么有什么区别呢?

在内核线程处理的事件:需要经过内核线程处理的输入事件要在内核线程执行逻辑,遇到内核线程在忙,无法立即响应。如用户的大部分输入事件都跟页面元素有关系,一旦页面元素注册了对应事件的监听器,监听器的逻辑代码(JavaScript)必须在内核线程中执行(V8引擎运行在内核线程),因此这种输入事件经常无法立即得到响应。
直接由合成线程处理的事件:不经过内核线程就能快速处理的输入事件为手势输入事件(滑动、捏合)

划重点:最骚的来了,虽然手势事件可以不在内核线程处理,但是手势事件的产生还是离不开内核线程。

页面卡顿的原因

手势事件有个属性 cancelable,作用是告诉浏览器该事件是否允许监听器通过 preventDefault() 方法阻止,默认为true。如果在touch事件内部调用preventDefault(),事件默认行为被取消,页面也就静止不动了。但是浏览器并不知道touch事件内部是否调用了preventDefault(),浏览器只有等内核线程执行到事件监听器对应的JavaScript代码时,才能知道内部是否会调用preventDefault函数来阻止事件的默认行为,所以浏览器本身无法优化这种场景。手势输入事件是由连续的普通输入事件组成的,在这种场景下,无法快速产生,会导致页面无法快速执行滑动逻辑,从而让用户感觉到页面卡顿。

而Chrome团队从统计数据中分析得出,注册了mousewheel/touch相关事件监听器的页面中,80%的页面内部都不会调用preventDefault函数来阻止事件的默认行为。对于这80%的页面,即使监听器内部什么都没有做,相对没有注册mousewheel/touch事件监听器的页面,在滑动流畅度上,有10%的页面增加至少100ms的延迟,1%的页面甚至增加500ms以上的延迟。Chrome团队认为对于统计中的这80%的页面来说,他们都是不希望因为注册mousewheel/touch相关事件监听器而导致滑动延迟增加的。

passive的诞生

所以,passive 监听器诞生了,passive 的意思是“顺从的”,表示它不会对事件的默认行为说 no,浏览器知道了一个监听器是 passive 的,它就可以在两个线程里同时执行监听器中的 JavaScript 代码和浏览器的默认行为了。

经过上面的分析,我们了解到了Passive Event Listeners特性实际上是为了解决浏览器页面滑动流畅度而设计的,它通过扩展事件属性passive让Web开发者来告知浏览器监听器是否会阻止事件的默认行为,从而让浏览器可以更智能地决策并优化,这其中涉及到了Chrome的多线程渲染框架、输入事件处理等知识。

总结

参考自:
https://blog.csdn.net/dj0379/...
http://www.cnblogs.com/ziyunf...

本文主要是对上面提及两篇文章的总结和整理,理顺一下自己的思路。如果我写得不够明白可以去看看两位大佬的文章。

原文地址:https://segmentfault.com/a/1190000017247263


http://chatgpt.dhexx.cn/article/HhwLCuoa.shtml

相关文章

Java并发编程—CompletableFuture的介绍和使用

在博主上一篇博客介绍中,Java并发编程—java异步Future的迭代过程_小魏快起床的博客-CSDN博客,这里面给大家分析了Future的使用过程和一些存在的问题,那么针对里面出现的阻塞问题,博主将在这一篇文章给大家介绍清楚 &#x1f34f…

Java8 CompletableFuture runAsync等使用学习总结 submit() execute()等

一般的 Executors 的 execute以及submit 并发包下 Executors 创建的线程存在 一个 execute(),以及三个 submit() 不同的是使用 execute() 执行的任务是没有返回值的,使用 submit() 则是存在返回值的,这与接下里要说的 CompletableFuture.run…

实现异步编程,这个工具类你得掌握!

前言 最近看公司代码,多线程编程用的比较多,其中有对CompletableFuture的使用,所以想写篇文章总结下 在日常的Java8项目开发中,CompletableFuture是很强大的并行开发工具,其语法贴近java8的语法风格,与st…

Java异步编程之CompletableFuture

异步任务 Future获取异步任务结果 利用 Java 并发包提供的 Future 可以很容易获得异步任务的执行结果,无论异步任务是通过线程池 ThreadPoolExecutor 执行的,还是通过手工创建子线程来执行的。利用多线程可以快速将一些串行的任务并行化,从而…

JUC异步编程

什么是JUC JUC的意思是java并发编程工具包,是java.util.concurrent包的简称。目的就是为了更好的支持高并发任务,让开发者利用这个包进行的多线程开发时,可以有效的减少竞争条件和死锁线程。 异步编程 模拟用户下单操作。。。 1、根据地址…

线程、多线程的使用、线程池、异步(CompletableFuture)-48

一:线程 1.初始化线程的四种方式 1)、继承 Thread public class ThreadTest {public static void main(String[] args) {System.out.println("main...start...");Thread01 thread new Thread01();//启动线程thread.start();System.out.pri…

CompletableFuture 执行异步任务

CompletableFuture 执行异步任务 参考: (10条消息) Java 8 的异步编程利器 CompletableFuture 真香!_不才陈某的博客-CSDN博客 提供几十种方法,帮助异步任务执行调用; 主要包括: 创建异步任务任务异步回调多个任务…

CompletableFuture实现异步编排全面分析和总结

一、🌈CompletableFuture简介 CompletableFuture结合了Future的优点,提供了非常强大的Future的扩展功能,可以帮助我们简化异步编程的复杂性,提供了函数式编程的能力,可以通过回调的方式处理计算结果,并且提…

【Java8新特性--->异步处理】CompletableFuture

一、引入 假设一个商品详情页需要以下操作: 查询展示商品的基本信息耗时:0.5s查询展示商品的销售信息耗时:0.7s查询展示商品的图片信息耗时:1s查询展示商品销售属性耗时:0.3s查询展示商品规格属性耗时:1.…

CompletableFuture API

目录 1. 为什么要用CompletableFuture1.1 API 2. CompletableFuture Demo1. 创建CompletableFuture2. 定义CompletableFuture完成时和异常时需要回调的实例3. CompletableFuture的优点 3. demo:多个CompletableFuture串行执行4. demo:多个CompletableFut…

CompletableFuture实战与分析

Future对于结果的获取不够好,只能通过阻塞或者轮询的方式得到任务的结果。在Java8中Doug Lea大师提供了一个CompletableFuture工具类,可以更优雅的对异步并行操作进行编排。 Future VS CompletableFuture CompletableFuture支持手动完成任务&#xff0…

Java8 CompletableFuture异步非阻塞做法

创建异步任务 Future.submit supplyAsync / runAsync 异步回调 thenApply / thenApplyAsync thenAccept / thenRun exceptionally whenComplete handle 组合处理 thenCombine / thenAcceptBoth / runAfterBoth applyToEither / acceptEither / runAfterEither thenCom…

2022.2.5 第十三次周报

文章目录 前言一、论文阅读《ROCKET: Exceptionally fast and accurate time series classification using random convolutional kernels》Abstract摘要Introduction介绍Method方法Kernels内核Transform转换Classifier分类器Complexity Analysis复杂性分析 Experiments实验Con…

并发编程(十五)-CompletableFuture中常用方法的使用与分析

文章目录 一、CompletableFuture API介绍1. 描述2. CompletionStage3. CompletableFuture 4个核心静态方法(1)runAsync(Runnable runnable)(2)runAsync(Runnable runnable, Executor executor)(3)supplyAsy…

Java 编程问题:十一、并发-深入探索

原文:Java Coding Problems 协议:CC BY-NC-SA 4.0 贡献者:飞龙 本文来自【ApacheCN Java 译文集】,自豪地采用谷歌翻译。 本章包括涉及 Java 并发的 13 个问题,涉及 Fork/Join 框架、CompletableFuture、ReentrantLock…

线程(十二)---CompletableFuture(三)

写在前面:各位看到此博客的小伙伴,如有不对的地方请及时通过私信我或者评论此博客的方式指出,以免误人子弟。多谢! 示例五:异常处理 接着上一篇记录一下CompletableFuture的异常处理,异常处理通常使用…

dice loss

Dice Loss 最先是在VNet 这篇文章中被提出,后来被广泛的应用在了医学影像分割之中。 Dice 系数 Dice系数作为损失函数的原因和混淆矩阵有着很大的关系,下图给出的是一个混淆矩阵: 其中的一些关键指标如下: 精确率(precision)表…

Hinge loss

声明: 参考自维基百科后面可能会更新 Hinge Loss 在机器学习中,hinge loss作为一个损失函数(loss function),通常被用于最大间隔算法(maximum-margin),而最大间隔算法又是SVM(支持向量机support vector machines)用到的重要算法…

【深度学习】一文读懂机器学习常用损失函数(Loss Function)

【深度学习】一文读懂机器学习常用损失函数(Loss Function) 最近太忙已经好久没有写博客了,今天整理分享一篇关于损失函数的文章吧,以前对损失函数的理解不够深入,没有真正理解每个损失函数的特点以及应用范围&#x…

Pytorch之loss(损失函数)

损失函数也在torch.nn下,具体可以参考文档,也可以参考官网 先根据L1Loss举例 我个人感觉这里的描述还是到官网的文档找比较好,公式看的比文档清楚 import torch from torch import nninputs torch.tensor([[3, 2, 1],[1, 2, 3]], dtypetorch…