刷《一年半经验,百度、有赞、阿里面试总结》·手记 (3)

第二种方法是利用CSS3的flex布局,父元素diplay属性设置为flex,并且定义元素在两条轴线的布局方式均为center

.wrap { display: flex; justify-content: center; align-items: center; width: 100vw; height: 100vh; } .wrap .box { width: 100px; height: 100px; }

第三种方法是利用margin负值来进行元素偏移,优点是浏览器兼容好,缺点是不够灵活(要自行计算margin的值):

.wrap { position: relative; width: 100vw; height: 100vh; } .box { position: absolute; top: 50%; left: 50%; width: 100px; height: 100px; margin: -50px 0 0 -50px; } 2.2 “点击”改变样式

题目:实现效果,点击容器内的图标,图标边框变成border 1px solid red,点击空白处重置。

利用event.target可以判断是否是指定元素本身(判断“空白处”),除此之外,注意禁止冒泡(题目指明了“容器内”)。

<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> <style> #app { min-width: 100vw; min-height: 100vh; } #app .icon{ display: inline-block; cursor: pointer; } </style> </head> <body> <div> <span>123456</span> </div> <script> const app = document.querySelector("#app") const icon = document.querySelector(".icon") app.addEventListener("click", e => { if(e.target === icon){ return; } // 非空白处才去除 border icon.style.border = "none"; }) icon.addEventListener("click", e => { // 禁止冒泡 e.stopPropagation() // 更改样式 icon.style.border = "1px solid red"; }) </script> </body> </html> 3. 浏览器/协议相关 3.1 缓存机制

题目:说一下浏览器的缓存机制。

浏览器缓存分为强缓存和协商缓存。缓存的作用是提高客户端速度、节省网络流量、降低服务器压力

强缓存:浏览器请求资源,如果header中的Cache-Control和Expires没有过期,直接从缓存(本地)读取资源,不需要再向服务器请求资源。

协商缓存:浏览器请求的资源如果是过期的,那么会向服务器发送请求,header中带有Etag字段。服务器再进行判断,如果ETag匹配,则返回给客户端300系列状态码,客户端继续使用本地缓存;否则,客户端会重新获取数据资源。

关于过程中详细的字段,可以参考这篇《http协商缓存VS强缓存》

3.2 从URL到页面生成

题目:输入URL到看到页面发生的全过程,越详细越好

DNS解析

建立TCP连接(3次握手)

发送HTTP请求,从服务器下载相关内容

浏览器构建DOM树和CSS树,然后生成渲染树。这个一个渐进式过程,引擎会力求最快将内容呈现给用户。

在第四步的过程中,<script>的位置和加载方式会影响响应速度。

搞定了,关闭TCP连接(4次握手)

3.3 TCP握手

题目:解释TCP建立的时候的3次握手和关闭时候的4次握手

看这题的时候,我也是突然懵(手动捂脸)。推荐翻一下计算机网络的相关书籍,对于FIN、ACK等字段的讲解很赞!

3.4 CSS和JS位置

题目:CSS和JS的位置会影响页面效率,为什么?

先说CSS。CSS的位置不会影响加载速度,但是CSS一般放在<head>标签中。前面有说DOM树和CSS树共同生成渲染树,CSS位置太靠后的话,在CSS加载之前,可能会出现闪屏、样式混乱、白屏等情况。

再说JS。JS是阻塞加载,默认的<script>标签会加载并且立即执行脚本,如果脚本很复杂或者网络不好,会出现很久的白屏。所以,JS标签一般放到<body>标签最后。

现在,也可以为<script>标签设置async或者defer属性。前者是js脚本的加载和执行将与后续文档的加载和渲染同步执行。后者是js脚本的加载将与后续文档的加载和渲染同步执行,当所有元素解析完,再执行js脚本。

4. 算法相关 4.1 数组全排列

题目:现在有一个数组[1,2,3,4],请实现算法,得到这个数组的全排列的数组,如[2,1,3,4],[2,1,4,3]。。。。你这个算法的时间复杂度是多少

实现思路:从“开始元素”起,每个元素都和开始元素进行交换;不断缩小范围,最后输出这种排列。暴力法的时间复杂度是 \(O(N_N)\),递归实现的时间复杂度是 \(O(N!)\)

如何去重?去重的全排列就是从第一个数字起每个数分别与它后面非重复出现的数字交换。对于有重复元素的数组,例如:[1, 2, 2],应该剔除重复的情况。每次只需要检查arr[start, i)中是不是有和arr[i]相同的元素,有的话,说明之前已经输出过了,不需要考虑。

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/wpdyys.html