1.CSS和JS在网页中的放置顺序是怎样的?
- CSS应该放在页面顶部的head标签中,html页面需要等到CSS解析完后才能完成渲染,所以CSS应放在head标签内,优先下载解析,以避免页面元素由于样式缺失造成瞬间的白页或者给用户闪烁感。
- JS应该放在body的底部,这是为了提高页面渲染的速度效率。浏览器在加载<script>元素内部的JS代码将被从上至下依次解释,解释器对<script>元素内部所有代码求值完毕之前,会阻塞其他资源的加载,页面的其余内容都不会被浏览器加载显示,如果放置在前面其他位置,会对页面内容的加载速度产生影响。
2.解释白屏和FOUC
- ie浏览器是在页面组件包括样式表全部加载完成后才呈现整个页面,等CSS加载完成之后,再对HTML元素进行渲染和展示,当CSS放在页面底部时,IE浏览器先加载HTML元素,再加载CSS,然后进行渲染并展示在页面上,耗时较长,将会出现白屏。出现白屏的另外两种情况:使用 @import 标签(可能导致页面组件下载时的无序性)、script标签放在前面(加载 JavaScript 时,会禁用并发,并且阻止其他内容的下载)
- Firefox浏览器对页面中的组件逐步呈现,当CSS位于页面底部,浏览器首先加载HTML元素并显示在页面上,此时html元素没有得到CSS的渲染而内容无样式,当页面底部的CSS加载完成后重新对样式进行修改,这就会产生FOUC(无样式内容闪烁)。
3.async和defer的作用是什么?有什么区别
作用:加载和渲染后续文档元素的过程将和 script.js 的加载与执行并行进行,如果没有 defer 或 async,浏览器会立即加载并执行指定的脚本,“立即”指的是在渲染该 script 标签之下的文档元素之前,也就是说不等待后续载入的文档元素,读到就加载并执行。
async和defer的区别主要在于script.js 的执行。
async的作用:加载和渲染后续文档元素的过程将和 script.js 的加载与执行并行进行。
defer的作用:加载后续文档元素的过程将和 script.js 的加载并行进行,但是 script.js 的执行要在所有元素解析完成之后,DOMContentLoaded 事件触发之前完成。
如果脚本涉及少量DOM操作,则defer属性更优:因为html解析未完成前,可能DOM tree未形成,此时进行DOM操作,可能失败。
如果是多个脚本,则其执行顺序为:
a、多个defer脚本,根据HTML5的规定,会按照定义的加载顺序,按序执行;
b、多个async脚本,由于加载完成立即执行,所以是乱序;因此其更适合脚本之间无依赖关系的情况。
然后从实用角度来说呢,首先把所有脚本都丢到 之前是最佳实践,因为对于旧浏览器来说这是唯一的优化选择,此法可保证非脚本的其他一切元素能够以最快的速度得到加载和解析。