十道前端面试题第【03】篇
2021-03-21 本文已影响0人
夏海峰
摘要:本篇分享了10道面试题——Web性能优化方案、JS严格模式、五道算法题、自定义JS事件系统、输入URL到浏览器渲染的全过程、HTTP和HTTPS相关。

1、你知道的 Web 性能优化方案有哪些?
2、什么是严格模式?严格模式下,代码有哪些规范?
3、封装函数 flat() ,实现数组的扁平化。
需求:所谓扁平化,就是将一个嵌套多层的数组,转换为只有一层的数组。示例如下:
var arr = [1, [2, [3, 4]]]
flat(arr) // [1, 2, 3, 4]
function flat(arr) {
return arr.reduce((prev, cur)=>{
return prev.concat(Array.isArray(cur) ? flat(cur) : cur)
}, [])
}
4、求柱状图中面积最大的矩形。
需求:给定 n
个非负整数,用来表示柱状图中各个柱子的高度。每个柱子彼此相邻,且宽度为 1
。求在该柱状图中,能够勾勒出来的矩形的最大面积。


# 暴力实现
function maxArea(arr) {
if (!arr || !arr.length) return 0
let maxArea = 0
for (let i = 0; i < arr.length; i++) {
let minHeight = Infinity
for (let j = i; j < arr.length; j++) {
minHeight = Math.min(minHeight, arr[j])
maxArea = Math.max(maxArea, (j - i + 1) * minHeight)
}
}
return maxArea
}
# 优化实现
function maxArea(arr) {
let maxArea = 0
const stack = []
arr = [0].concat(arr).concat([0])
for (let i = 0; i < arr.length; i++) {
while (stack && arr[stack[stack.length - 1]] > arr[i]) {
const j = stack.pop()
maxArea = Math.max((i - stack[stack.length - 1] - 1) * arr[j], maxArea)
}
stack.push(i)
}
return maxArea
}
5、封装快速排序算法。

const quickSort = arr => {
const a = [...arr];
if (a.length < 2) return a;
const pivotIndex = Math.floor(arr.length / 2);
const pivot = a[pivotIndex];
const [lo, hi] = a.reduce(
(acc, val, i) => {
if (val < pivot || (val === pivot && i != pivotIndex)) {
acc[0].push(val);
} else if (val > pivot) {
acc[1].push(val);
}
return acc;
},
[[], []]
);
return [...quickSort(lo), pivot, ...quickSort(hi)];
};
6、封装选择排序算法。

const selectionSort = arr => {
const a = [...arr];
for (let i = 0; i < a.length; i++) {
const min = a
.slice(i + 1)
.reduce((acc, val, j) => (val < a[acc] ? j + i + 1 : acc), i);
if (min !== i) [a[i], a[min]] = [a[min], a[i]];
}
return a;
};
7、封装插入排序算法。

const insertionSort = arr =>
arr.reduce((acc, x) => {
if (!acc.length) return [x];
acc.some((y, j) => {
if (x <= y) {
acc.splice(j, 0, x);
return true;
}
if (x > y && j === acc.length - 1) {
acc.splice(j + 1, 0, x);
return true;
}
return false;
});
return acc;
}, []);
8、自定义实现一个 JS 事件系统。
- 自定义
EventBus
类,它的eventArr
属性用于存放所有注册成功的自定义事件,这是一个事件容器。 - 原型链上的
on()
方法,用于绑定一个自定义事件,这类事件可以被多次触发。 - 原型链上的
once()
方法,用于绑定只能被触发一次的自定义事件。 - 原型链上的
off()
方法,用于解绑指定的自定义事件。 - 原型链上的
emit()
方法,用于触发事件容器中的指定类型的自定义事件。
function Event() {
this.eventArr = []
}
// on() 方法,用于绑定一个自定义事件
Event.prototype.on = function (eventType, callbackFn) {
this.eventArr.push({
eventType,
callbackFn,
once: false,
done: false
})
}
// once() 方法,用于绑定只能触发一次的自定义事件
Event.prototype.once = function (eventType, callbackFn) {
this.eventArr.push({
eventType,
callbackFn,
once: true,
done: false
})
}
// off() 方法,用于解绑自定义事件
Event.prototype.off = function (eventType, callbackFn) {
this.eventArr.map((ele, idx) => {
if (ele.eventType === eventArr && ele.callbackFn === callbackFn) {
this.eventArr.splice(idx, 1)
}
})
}
// emit() 方法,用于触发事件模型中指定类型的自定义事件
Event.prototype.emit = function (eventType) {
this.eventArr.map((ele, idx) => {
if (ele.eventType === eventType) {
if (!ele.done) {
ele.callbackFn()
if (ele.once) {
this.eventArr[idx].done = true // 把once注册的事件,标记为“done”
}
}
}
})
}
// 测试一下
const bus = new Event()
bus.on('xxx', ()=>console.log('xxx'))
bus.emit('xxx')
9、描述浏览器输入URL到页面渲染的整个过程。
- 浏览器的地址栏输入URL并按下回车;
- DNS 解析:将域名解析成 IP 地址;
- TCP 连接:TCP 三次握手;(三次握手的目的:为了防止已经失效的连接请求报文段突然又传送到了服务器端,从而产生错误)
- 发送 HTTP 请求;
- 服务器处理请求并返回 HTTP 报文;
- 浏览器解析渲染页面;
- 断开连接:TCP 四次挥手。


10、HTTP和HTTPS有哪些区别?HTTP报文由哪些部分组成?
HTTPS = HTTP + 加密 + 身份验证 + 数据完整性保护。
从 HTTP 协议栈层面来看,我们可以在 TCP 和 HTTP 之间插入一个安全层,所有经过安全层的数据都会被加密或者解密(如下图所示)。

本周结束,下周继续!!!