HTML浏览器缓存问题(涉及到:http强缓存与协商缓存)

  5.缓存问题(涉及到:http强缓存与协商缓存,缓存头,etag,expired,cache-control等)

  6.浏览器接受到http数据包后的解析流程(涉及到html词法分析,解析成DOM树,解析CSS生成CSSOM树,合并生成render渲染树。然后layout布局,painting渲染,复合图层合成,GPU绘制,外链处理等)

  7.css可视化模型(涉及到:元素渲染规则,如:包含块,控制框,BFC,IFC等)

  8.JS引擎解析过程(涉及到:JS解析阶段,预处理阶段,执行阶段生成执行上下文,VO(全局对象),作用域链,回收机制等)

  你会发现一个简单的输入URL到页面呈现,之间会发生这么多过程,是不是瞬间觉得崩溃了?(别急,这一章我们不讲这么深,先教你如何回答这个问题,后面这一节单独出文章讲)

  线程对渲染的影响_mfc创建ui线程_js单线程 ui渲染

  4.浏览器是如何解析代码的?解析HTML

  HTML是逐行解析的,浏览器的渲染引擎会将HTML文档解析并转换成DOM节点。

  解析CSS

  浏览器会从右往左解析CSS选择器

  我们知道DOM树与CSSOM树合并成render树,实际上是将CSSOM附着到DOM树上,因此需要根据选择器提供的信息对DOM树进行遍历。

  我们看一个例子?:

  

    .nav .title span {color:blue}
    
    
      
        南玖
      
      前端
    

  从右至左的匹配:

  先找到所有的最右节点 span,对于每一个 span,向上寻找节点 div.title由 h3再向上寻找 div.nav 的节点最后找到根元素 html 则结束这个分支的遍历。解析JS

  在浏览器中有一个js解析器的工具,专门用来解析我们的js代码

  当浏览器遇到js代码时,立马召唤“js解析器”出来工作。

  解析器会找到js当中的所有变量、函数、参数等等,并且把变量赋值为未定义(undefined)。

  把函数取出来成为一个函数块,然后存放到仓库当中。这件事情做完了之后才开始逐行解析代码(由上向下,由左向右),然后再去和仓库进行匹配。

  5.DOMContentLoaded与load的区别?6.浏览器重绘域重排的区别?

  重绘不一定导致重排,但重排一定绘导致重绘

  如何触发重绘和重排?

  任何改变用来构建渲染树的信息都会导致一次重排或重绘:

  如何避免重绘或重排?

  提升合成层的最好方式是使用 CSS 的 will-change 属性:

   #target {

      will-change: transform;
    }

  7.为什么JS是单线程的?

  这主要与JS的用途有关,JS作为浏览器的脚本语言,最初主要是实现用户与浏览器的交互,以及操作DOM。这就决定了它只能是单线程,否则会带来许多复杂的同步问题。

  举个例子?: 如果JS是多线程的,其中一个线程要修改一个DOM元素,另外一个线程想要删除这个DOM元素,这时候浏览器就不知道该听谁的。所以为了避免复杂性js单线程 ui渲染,从一诞生,JavaScript就被设计成单线程。

  为了利用多核CPU的计算能力,HTML5提出Web Worker标准,允许JavaScript脚本创建多个线程,但是子线程完全受主线程控制,且不得操作DOM。所以,这个新标准并没有改变JavaScript单线程的本质

  8.CSS加载会阻塞DOM吗?先上结论CSSOM的作用

  由之前讲到的浏览器渲染流程我们可以看出:

  JS需要等待CSS的下载,这是为什么呢?(CSS阻塞DOM执行)

  如果JS脚本的内容是获取元素的样式,那它就必然依赖CSS。因为浏览器无法感知JS内部到底想干什么,为避免样式获取,就只好等前面所有的样式下载完毕再执行JS。但JS文件与CSS文件下载是并行的,CSS文件会在后面的JS文件执行前先加载执行完毕,所以CSS会阻塞后面JS的执行

  避免白屏,提高CSS的加载速度9.JS会阻塞页面吗?先上结论

  JS会阻塞DOM的解析,因此也就会阻塞页面的加载

  这也是为什么我们常说要把JS文件放在最下面的原因

  由于 JavaScript 是可操纵 DOM 的,如果在修改这些元素属性同时渲染界面(即 JavaScript 线程和 UI 线程同时运行),那么渲染线程前后获得的元素数据就可能不一致了。

  因此为了防止渲染出现不可预期的结果,浏览器设置 「GUI 渲染线程与 JavaScript 引擎为互斥」的关系。

  当 JavaScript 引擎执行时 GUI 线程会被挂起,GUI 更新会被保存在一个队列中等到引擎线程空闲时立即被执行。

  当浏览器在执行 JavaScript 程序的时候,GUI 渲染线程会被保存在一个队列中,直到 JS 程序执行完成,才会接着执行。

  因此如果 JS 执行的时间过长,这样就会造成页面的渲染不连贯,导致页面渲染加载阻塞的感觉。

  mfc创建ui线程_线程对渲染的影响_js单线程 ui渲染

  10.defer和async的区别?11.浏览器的垃圾回收机制

  垃圾回收是一种自动的内存管理机制。当计算机上的动态内存不再需要时,就应该予以释放。

  需要注意的是,自动的意思是浏览器可以自动帮助我们回收内存垃圾,但并不代表我们不用关心内存管理,如果操作不当,JavaScript中仍然会出现内存溢出的情况,造成系统崩溃。

  由于字符串,数组,对象等都没有固定大小,因此需要当它们大小已知时,才能对他们进行动态的存储分配。JavaScript程序每次创建字符串,数组或对象时,解释器都必须分配内存来存储那个实体。

  JavaScript解释器可以检测到何时程序不在使用一个对象了,当它确定这个对象是无用的时候,他就知道不再需要这个对象了,就可以把它占用的内存释放掉了。

  浏览器通常采用的垃圾回收有两种方法:标记清除,引用计数。

  标记清除

  这是JavaScript中最常用的垃圾回收方式

  从2012年起,所有现代浏览器都使用了标记清除的垃圾回收方法,除了低版本IE还是采用的引用计数法。

  那么什么叫标记清除呢?

  JavaScript中有一个全局对象,定期的,垃圾回收器将从这个全局对象开始,找出所有从这个全局对象开始引用的对象,再找这些对象引用的对象...对这些活跃的对象标记,这是标记阶段。清楚阶段就是清楚那些没有被标记的对象。

  标记清除有一个问题,就是在清除之后,内存空间是不连续的,即出现了内存碎片。如果后面需要一个比较大的连续的内存空间,那将不能满足要求。而标记整理 方法可以有效德地解决这个问题。

  在标记的过程中,引入了概念:三色标记法,三色为:

  标记整理:

  标记阶段与标记清除法没什么区别,只是标记结束后,标记整理法会将存活的对象向内存的一边移动,最后清理掉边界内存。

  引用计数

  引用计数的含义是跟踪记录每个值被引用的次数。当一个变量A被赋值时,这个值的引用次数就是1,当变量A重新赋值后,则之前那个值的引用次数就减1。当引用次数变成0时,则说明没有办法再访问这个值了,所以就可以清除这个值占用的内存了。

  大多数浏览器已经放弃了这种回收方式

  内存泄漏

  为避免内存泄漏,一旦数据不再使用,最好通过将其值设为null来释放其引用,这个方法叫做接触引用

  哪些情况会造成内存泄漏?如何避免?

  以 Vue 为例,通常有这些情况:

  解决办法:beforeDestroy 中及时销毁

  浏览器中不同类型变量的内存都是何时释放的?基本类型12.说一说浏览器的缓存机制?认识浏览器缓存

  当浏览器请求一个网站时,会加载各种资源,对于一些不经常变动的资源,浏览器会将他们保存在本地内存中,下次访问时直接加载这些资源,提高访问速度。

  如何知道资源是请求的服务器还是读取的缓存呢?

  线程对渲染的影响_mfc创建ui线程_js单线程 ui渲染

  看上面这张图,有些资源的size值是大小,有些是from disk cache,有些是from memory cache,显示大小的是请求的服务器资源,而显示后面两种的则是读取的缓存。

  -memory cachedisk cache

  相同点

  只能存储一些派生类资源文件

  只能存储一些派生类资源文件

  不同点

  退出进程时数据会被清除

  退出进程时数据不会被清除

  存储资源

  一般脚本、字体、图片会存在内存当中

  一般非脚本会存在内存当中,如css等

  浏览器缓存分类

  浏览器在向服务器请求资源时,首先判断是否命中强缓存,没命中再判断是否命中协商缓存

  mfc创建ui线程_js单线程 ui渲染_线程对渲染的影响

  强缓存

  浏览器在加载资源时js单线程 ui渲染,会先根据本地缓存资源的header中判断是否命中强缓存,如果命中则直接使用缓存中的资源,不会再向服务器发送请求。(这里的header中的信息指的是 expires 和 cache-control)

  Expires

  该字段是 http1.0 时的规范,它的值为一个绝对时间的 GMT 格式的时间字符串,比如 Expires:Mon,18 Oct 2066 23:59:59 GMT。这个时间代表着这个资源的失效时间,在此时间之前,即命中缓存。这种方式有一个明显的缺点,由于失效时间是一个绝对时间,所以当服务器与客户端时间偏差较大时,就会导致缓存混乱。所以这种方式很快在后来的HTTP1.1版本中被抛弃了。

  Cache-Control

  Cache-Control 是 http1.1 时出现的 header 信息,主要是利用该字段的 max-age 值来进行判断,它是一个相对时间,例如 Cache-Control:max-age=3600,代表着资源的有效期是 3600 秒。cache-control 除了该字段外,还有下面几个比较常用的设置值:

  no-cache:需要进行协商缓存,发送请求到服务器确认是否使用缓存。

  no-store:禁止使用缓存,每一次都要重新请求数据。

  public:可以被所有的用户缓存,包括终端用户和 CDN 等中间代理服务器。

  private:只能被终端用户的浏览器缓存,不允许 CDN 等中继缓存服务器对其缓存。

  Cache-Control 与 Expires 可以在服务端配置同时启用,同时启用的时候 Cache-Control 优先级高。

  协商缓存

  当强缓存没命中时,浏览器会发送一个请求到服务器,服务器根据 header 中的信息来判断是否命中协商缓存。如果命中,则返回304 ,告诉浏览器资源未更新,可以使用本地缓存。(这里的header信息指的是Last-Modify/If-Modify-Since 和 ETag/If-None-Match)

  Last-Modify/If-Modify-Since

  浏览器第一次请求一个资源的时候,服务器返回的 header 中会加上 Last-Modify,Last-modify 是一个时间标识该资源的最后修改时间。

  当浏览器再次请求该资源时,request 的请求头中会包含 If-Modify-Since,该值为缓存之前返回的 Last-Modify。服务器收到 If-Modify-Since 后,根据资源的最后修改时间判断是否命中缓存。

  如果命中缓存,则返回 304,并且不会返回资源内容,并且不会返回 Last-Modify。

  缺点:

  短时间内资源发生了改变,Last-Modified 并不会发生变化。

  周期性变化。如果这个资源在一个周期内修改回原来的样子了,我们认为是可以使用缓存的,但是 Last-Modified 可不这样认为,因此便有了 ETag。

  mfc创建ui线程_线程对渲染的影响_js单线程 ui渲染

  ETag/If-None-Match

  与 Last-Modify/If-Modify-Since 不同的是,Etag/If-None-Match 返回的是一个校验码。ETag 可以保证每一个资源是唯一的,资源变化都会导致 ETag 变化。服务器根据浏览器上送的 If-None-Match 值来判断是否命中缓存。

  与 Last-Modified 不一样的是,当服务器返回 304 Not Modified 的响应时,由于 ETag 重新生成过,response header 中还会把这个 ETag 返回,即使这个 ETag 跟之前的没有变化。

  Last-Modified 与 ETag 是可以一起使用的,服务器会优先验证 ETag,一致的情况下,才会继续比对 Last-Modified,最后才决定是否返回 304。

  总结

  当浏览器访问一个已经访问过的资源是,它的步骤是:

  1.先看是否命中强缓存,命中?的话直接使用缓存

  2.没命中强缓存,则会发送请求到服务器看是否命中?协商缓存

  3.如果命中了协商缓存,服务器会返回304告诉浏览器可以使用本地缓存

  4.没命中协商缓存,则服务器会返回新的资源给浏览器

  13.什么是浏览器的同源策略,以及跨域?同源策略

  同源策略是浏览器的一种自我保护行为。所谓的同源指的是:协议,域名,端口均要相同

  浏览器中大部分内容都是受同源策略限制的,但是以下三个标签不受限制:

   线程对渲染的影响_mfc创建ui线程_js单线程 ui渲染

  跨域

  跨域指的是浏览器不能执行其它域名下的脚本。它是由浏览器的同源策略限制的。

  你可能会想跨域请求到底有没有发送到服务器?

  事实上,跨域请求时能够发送到服务器的,并且服务器也能过接受的请求并正常返回结果,只是结果被浏览器拦截了。

  跨域解决方案(列出几个常用的)JSONP

  它主要是利用script标签不受浏览器同源策略的限制,可以拿到从其他源传输过来的数据,需要服务端支持。

  优缺点:

  兼容性比较好,可用于解决主流浏览器的跨域数据访问的问题。缺点就是仅支持get请求,具有局限性,不安全,可能会受到XSS攻击。

  思路:

文章由官网发布,如若转载,请注明出处:https://www.veimoz.com/1907
0 评论
761

发表评论

!