回答这题的思路要从另外一道面试题:从敲回车开始到页面展示这个过程发生了什么入手。如下是其中的一些过程:css
<link href='#'>,<script src='#'>
就会像服务器发起请求优化以上每一个步骤,这样子整个web网页的性能就提升了html
你在浏览器地址栏输入网址,经过DNS查询获得网站真实IP。前端
好比你的一个网站,须要向 baidu.com 请求一个js文件,向 bootcdn.cn 请求一个css文件,这样子就要进行2次dns查询(没有dns缓存的状况下),解决方法就是各类资源放在数量尽可能少的域名下java
把资源分散到不一样的域名容许你最大化并行下载数git
例如chrome,只能同时向一个域名最多发8个请求,把资源分散到不一样的域名容许你最大化并行下载数,但这样子dns查询时间就变长,和前面的“减小dns查询“冲突了github
若是文件不多,例如只有3个文件,放在1个域名下,这样dns查询时间就很快,此时若是把这3个文件分散到更多的域名下,速度也不会提升,由于3个请求尚未达到chrome的只能同时向一个域名最多发请求的数量的极限web
若是文件不少,例如16个文件,还所有放在1个域名下,虽然dns查询时间很快,但请求时间会很慢,由于只能同时向一个域名最多发8个请求,那另外8个请求要等前面的请求发送完才能再发送面试
懒加载就是例如打开一个网页,viewport如下的网页内容先不加载,等到用户滚动看到那部份内容再加载相应的资源,好处:节省CDN费用,下降服务器压力chrome
预加载就是预先加载用户即将要看到的内容,例如当你在第一页时就预先加载第二页的内容,这样子用户打开第二页的时候就不用等待加载时间npm
cdn即内容分发网络,例如谷歌的主服务器1在美国,在北京有个服务器2,服务器2不断地把主服务器1上的内容复制过来(可能说得不是很准确),这样子在北京访问谷歌,直接访问北京的服务器,比你访问美国的主服务器要快
从HTTP/1.1
开始,客户端经过http请求中的Accept-Encoding
头部来提示支持的压缩:
Accept-Encoding: gzip, deflate
若是服务器看到这个头部,它可能会选用列表中的某个方法压缩要请求的资源。服务器经过响应中的Content-Encoding
头部提示客户端:
Content-Encoding: gzip
客户端接收到响应后会解压缩
gzip通常可减少响应的70%。尽量去gzip更多(文本)类型的文件。html,脚本,样式,xml和json等等都应该被gzip,而图片,pdf等等不该该被gzip,由于它们自己已被压缩过,gzip它们只是浪费cpu,甚至增长文件大小。
//后台代码 if (path ==='/js/main.js') { let string = fs.readFileSync('./js/main.js', 'utf8'); response.setHeader('Content-Type', 'application/javasript;charset=utf-8'); response.setHeader('Cache-Control', 'max-age=30'); response.write(string); response.end() }
max-age=30指当第一次请求并下载/js/main.js后,30s内遇到一样/js/main.js的请求(例如刷新当前页面),会从缓存里直接读取main.js,不会再向服务器发请求
静态资源:将 Expires 响应头设置为未来很远的时间,实现「永不过时」策略;
动态资源:设置合适的 Cache-Control 响应头,让浏览器有条件地发起请求。
在典型用法中,当一个URL被请求,Web服务器会返回资源和其相应的ETag值,它会被放置在HTTP的“ETag”字段中:
ETag: "686897696a7c876b7e"
而后,客户端能够决定是否缓存这个资源和它的ETag。之后,若是客户端想再次请求相同的URL,将会发送一个包含已保存的ETag和“If-None-Match”字段的请求。
If-None-Match: "686897696a7c876b7e"
客户端请求以后,服务器可能会比较客户端的ETag和当前版本资源的ETag。若是ETag值匹配,这就意味着资源没有改变,服务器便会发送回一个极短的响应,包含HTTP “304 未修改”的状态。304状态告诉客户端,它的缓存版本是最新的,并应该使用它。
然而,若是ETag的值不匹配,这就意味着资源极可能发生了变化,那么,一个完整的响应就会被返回,包括资源的内容,就好像ETag没有被使用。这种状况下,客户端能够用新返回的资源和新的ETag替代先前的缓存版本。
部分的后台Node.js示例代码:
上图代码的md5(string)能输出string的md5值,用的是https://www.npmjs.com/package... ,170k指的是string的大小
当浏览器请求静态图片并把cookie一块儿发送到服务器时,cookie此时对服务器没什么用处。因此这些cookie只是增长了网络流量。因此你应该保证静态资源的请求是没有cookie的。能够建立一个子域名来托管全部静态组件。
好比,你域名是www.example.org
,能够把静态资源托管在static.example.org
。不过,你若是把cookie设置在顶级域名example.org
下,这些cookie仍然会被传给static.example.org
。这种状况下,启用一个全新的域名来托管静态资源
另一个用没有cookie的域名提供资源的好处是,某些代理可能会阻止缓存待cookie的静态资源请求。
Cookie:sessionId=44438.40790818172
http cookie的使用有多种缘由,好比受权和个性化。cookie的信息经过http头部在浏览器和服务器端交换。尽量减少cookie的大小来下降响应时间。
<link>
而不是@import
。以前的一个最佳原则是说CSS应该在顶部来容许逐步渲染。
在IE用@import
和把CSS放到页面底部行为一致,因此最好别用
有如下几个技术:
background-image
和 background-position
来显示不一样部分。data:url scheme
来內连图片。真实世界中使用外部文件通常会加快页面,由于JS和CSS文件被浏览器缓存了。內连的JS和CSS怎在每次HTML文档下载时都被下载。內连减小了http请求,但增长了HTML文档大小。另外一方面,若是JS和CSS被缓存了,那么HTML文档能够减少大小而不增长HTTP请求。
核心因素,就是JS和CSS被缓存相对于HTML文档被请求的频率。尽管这个因素很难被量化,但能够用不一样的指标来计算。若是网站用户每一个session有多个pv,许多页面重用相同的JS和CSS,那么有很大可能用外部JS和CSS更好。
惟一例外是內连更被主页偏心,如http://www.yahoo.com/
主页每一个session可能只有少许的甚至一个pv,这时候內连可能更快
对多个页面的首页来讲,能够经过技术减小(其它页面的)http请求。在首页用內连,初始化后动态加载外部文件,接下来的页面若是用到这些文件,就可使用缓存了。
压缩就是删除代码中没必要要的字符来减少文件大小,从而提升加载速度。当代码压缩时,注释删除,不须要的空格(空白,换行,tab)也被删除。
混淆是对代码可选的优化。它比压缩更复杂,而且可能产生bug。在对美国top10网站的调查,压缩可减少21%,而混淆可减少25%。
除了外部脚本和样式,內连的脚本和样式一样应该被压缩。
有时候页面看起来不那么响应(响应速度慢),是由于绑定到不一样元素的大量事件处理函数执行太屡次。这是为何要使用事件委托
另外,你没必要等到onload
事件来开始处理DOM树,DOMContentLoaded
更快。大多时候你须要的只是想访问的元素已在DOM树中,因此你没必要等到全部图片被下载。
在设计师建好图片后,在上传图片到服务器前你仍能够作些事:
pngcrush
或其它工具压缩png。jpegtran
或其它工具压缩jpeg。在 HTTP/1.0 时代,每个请求都会从新创建一个 TCP 链接,一旦响应返回,就关闭链接。 而创建一个链接,则须要进行三次握手(https的话则是9次握手),这极大的浪费了性能
所以 HTTP/1.1 新增了「keep-alive」功能,当浏览器创建一个 TCP 链接时,新的请求能够在上次创建的tcp链接之上发送,链接能够复用。。(现现在大多数浏览器默认都是开启的)
HTTP/2.0 时代拥有了「多路复用」功能,意思是: 在一条链接上,我能够同时发起无数个请求,而且响应能够同时返回。
问题:一个1M的JS文件,如何下载比较快?
理论上答案是3.这样能够并行下载4个文件,减小了带宽的占据,可是增长了3次TCP请求时间,在下载时间和TCP请求时间的取舍上,就要具体状况具体测试分析了。
若是是移动端就选择方案1,由于移动端对多文件下载不友好
若是选择第3种方案,那么引生出另外一个问题:为何不分得更多?
答:每一个浏览器对并行下载有上限。每一个域名限制最多同时进行N个下载线程。
<link href=''>
和<style>
放<head>
里面,由于不管放在那里都会阻塞html渲染(等到css文件下载并解析完才会显示html内容),因此还不如放head里面让css文件尽早下载
js放body最后,这样子能够获取html节点,且能先尽早显示html页面
chrome devtool的audits panel能够检测网站的性能优化状况
参考资源: