文章目录
- 前言
- 面试题
-
- 一、浏览器的地址栏输入url到显示页面的步骤?
- 二、http状态码及其含义?
- 三、js事件循环机制以及宏任务、微任务
- 四、== 和===的区别,在此期间js做了什么事情?
- 五、this的指向问题
- 六、call、apply、bind的区别?
- 七、new操作符的执行过程?
- 八、闭包是什么?如何创建闭包?闭包能做什么?
- 九、JS数据类型有哪些?以及判断数据类型有哪些方法,并手写函数返回类型
- 十、事件流模型有哪些?可以详细讲解一下吗?
- 十一、 谈谈MVC、MVP以及MVVM
- 十二、hash和history是什么东西?实现的原理是什么?具体讲一讲
- 十三、谈谈Vue的生命周期
- 十四、谈谈虚拟DOM
- 十五、cookie、localStorage和sessionStorage 三者之间的区别
- 十六、谈谈web开发中常见的网络安全问题
- 总结
前言
本人近期在准备前端暑期实习,为了更好地了解自己的学习情况,特从牛客网上找到热心网友发布的一些面经,然后自己整理一下,当做面试前的复习资料,也可以查漏补缺。今天整理的是微众银行的前端面试题。
面试题
一、浏览器的地址栏输入url到显示页面的步骤?
- 解析url。将url解析为协议、主机、端口、路径等信息。然后构造一个http请求。
- 在发送http请求之前,判断请求的资源是否在浏览器缓存中。这里的缓存有两个:强缓存和协商缓存。通过请求头的expires和cache-control字段判断是否命中强缓存。当强缓存失效后,浏览器将携带Last-modified/if-Modified-Since字段或者etag/if-None-Match字段向服务器发起请求,服务器根据浏览器携带的标识决定是否使用协商缓存。若使用协商缓存,则返回缓存中的资源和304状态码,若不使用协商缓存,则向服务器发起请求。
- 通过DNS解析获得url中的域名的IP地址。
- 通过TCP的三次握手,建立双方的连接。
- 当TCP握手结束后,会进行TLS四次握手,确保传输的安全性,然后就开始正式的传输数据。
- 假设返回的数据是HTML,则浏览器会解析HTML,然后创建一个DOM树。并行请求css/image/js。
- 浏览器解析css代码、计算出最终的样式数据,构造CSSOM树。
- 根据DOM树和CSSOM树构建渲染树,渲染树构建好之后,会根据渲染树来进行布局。
- 布局完成后,浏览器调用GPU进行绘制,合成图层,将内容显示在屏幕上。
- 最后一步是TCP断开连接的四次挥手的过程。
二、http状态码及其含义?
- 101:切换请求协议,从HTTP切换到WebSocket
- 200:请求成功,有响应体
- 301:永久重定向,会缓存
- 302:临时重定向。不会缓存
- 304:协商缓存命中
- 400:请求错误
- 403:服务器禁止访问
- 404:资源未找到
- 500:服务器错误
- 503:服务器繁忙
三、js事件循环机制以及宏任务、微任务
1.什么是事件循环?
- js主线程是有一个执行栈的,所有的js代码都会在执行栈里运行。在执行代码过程中,如果遇到异步的代码,比如:setTimeout、promise、async/await等,js就会将它们放在幕后线程中等待,不阻塞主线程的执行。当幕后线程中的代码已经准备好了(比如SetTimeout时间到了),该线程就会将它的回调函数放到任务队列中等待执行。当主线程中执行完栈中的所有代码后,它会检查任务队列中是否有任务要执行,如果有任务要执行的话,那么该任务就放到执行栈中执行。如果当前任务队内为空的话,它就会一直循环等待任务的到来,这就是js的事件循环机制。
2.任务队列
-
js有两个任务队列,宏任务队列和微任务队列。常见的宏任务有:setTimeout、setInterval、以及用户操作和UI渲染等。常见的微任务有:promise、async/await等。
-
事件循环的过程如下所示:
1)检查宏任务队列是否为空,若不为空,则进行下一步。若为空,则进行第3步;
2)从宏任务队内中取队首的任务进入执行栈中执行,执行完后进入下一步;
3)检查微任务队列是否为空,若不为空,则进行下一步。若为空,则进行第一步(开始新的事件循环
4)从微任务中取出队首的任务进去执行栈中执行,执行完成后进行第3步,在执行过程中新增的微任务会在当前事件循环周期内执行,而新增的宏任务只能等到下一个事件循环才能执行。总结一句话:一次事件循环只执行处于宏任务队首的任务,执行完成后,立即执行微任务队列中的所有任务。
注意:由于在执行为微任务的时候,只有当微任务队列为空的时候,才会进入下一个事件循环。因此,如果它源源不断地产生新的微任务,就会导致主线程一直在执行微任务,而没有办法执行宏任务,我们也就无法进行UI渲染以及接口请求数据了,因此,需要避免这种情况发生。
大家可以通过下面这个代码加深大家对事件循环执行顺序的理解:
console.log(1)
setTimeout(function() {
//settimeout1
console.log(2)
}, 0);
const intervalId = setInterval(function() {
//setinterval1
console.log(3)
}, 0)
setTimeout(function() {
//settimeout2
console.log(10)
new Promise(function(resolve) {
//promise1
console.log(11)
resolve()
})
.then(function() {
console.log(12)
})
.then(function() {
console.log(13)
clearInterval(intervalId)
})
}, 0);
//promise2
Promise.resolve()
.then(function() {
console.log(7)
})
.then(function() {
console.log(8)
})
console.log(9)
//执行结果:1 9 7 8 2 3 10 11 12 13
四、== 和===的区别,在此期间js做了什么事情?
首先 == 代表的是相等,===代表的是严格相等。在进行 == 比较的时候,会先进行两个操作数类型的判断,如果类型相同,则进行 === 比较,如果不同,则会进行隐式转换,转换成相同类型后再进行比较。而 === 比较的时候,如果类型不相同,则直接是false。
在进行 ==比较的时候,js是做了隐式转换这件事情的。
五、this的指向问题
this的指向主要有以下三种情况:
- 以函数形式调用的时候,this 永远指向window;
- 以方法的形式调用的时候,this指向调用方法的那个对象;
- 以构造函数调用的时候,this指向那个新创建的对象;
可通过下面这道题看自己是否掌握this的指向:
var name = 222
var a = {
name: 111,
say: function(){
console