知道PDD面试官水平贼高,所以抱着学习和接受拷打的心态来面这场二面了,果然不出所料,问的很有深度,除去汗流浃背的感觉以外还是收获到很多东西的,复盘一下。
基本全是场景题,考察设计,并且逐步深入完善。
1.为什么选择前端
2.有尝试过别的岗位吗,比如后端
3.如果想要设置一个定时器,每隔五秒打印一个“hello world”如何实现(回答了setTimeout递归、setInterval、Promiose等方法)
4.为什么setInterval定时可能不准确
5.用递归的方式实现一下(这个写了个最基础的版本,很简单)
function printHello() {
console.log('Hello');
setTimeout(printHello, 5000);
}
printHello();
6.这个setTimeout跟我设置一个setInterval这种方式去定时,在运行了很长一段时间之后会有什么差异(时间无限长,可能一年两年都行)?
复盘了一下,我觉得我回答的有问题,我是有提到setTimeout和setInterval的执行时机有区别的,但是好像在回答这个问题的时候没有get到面试官的意思。
应该是这样的:setTimeout是在你设置的时间之后才去执行要执行的语句(上一次的结束到下一次的开始是你delay的间隔),setInterval是不受你执行语句的耗时影响的(上一次的开始到下一次的开始是你delay的间隔)。所以重点应该是这个:当需要执行的语句耗时比较久的时候,可能会造成setInterval在某个时间点的某一次操作被跳过,大概是下面这个图:
(表述可能不是很清楚,大家有兴趣可以看一下连接:https://blog.51cto.com/xuqin/949052)
7.上面这种对精确性的影响在肉眼观察下是什么表现?
8.对上面的代码优化,需要运行一段时间之后关闭定时器,怎么修改?
let timer;
function printHello() {
console.log('Hello');
timer = setTimeout(printHello, 5000);
}
setTimeout(() => {
clearTimeout(timer);
}, 10000)
printHello();
9.上面这种没问题,如果换一种思路,不用全局变量来写呢?(这个就没做出来了,写了一半吧可能,但是有问题,这个问题想了很久)
function printHello(delay) {
console.log('hello');
let timer = setTimeout(printHello, 5000);
function clearTimer() {
if (timer) {
clearTimeout(timer);
console.log("clear");
}
}
setTimeout(clearTimer, delay);
}
printHello(10000);
问题在于,使用局部变量之后,并不能够很好的清除定时器,并且我下来自己调试了一下,clear会打印两次。我觉得就是因为每次递归调用的时候都是独立的函数作用域,clear只能清除掉当前作用域的?希望有好兄弟指点,这个确实看了好久不太会。
10.上面出现了两个问题,第一清除不掉,第二是不够灵活(在执行前就需要输入停止时间),想一下怎么修改。(这一块想了很久没想出来)
11.第二个场景题:给了两个函数①const api = () => {},返回一个promise②const warning = () => {}发出一个警告
现在需要对这两个函数进行封装,不需要改这两个函数,在调用api之后5s内如果没有拿到返回的promise,那就要调用warning。
前面那个题没搞出来就影响后面的思路了,这个一开始想着怎么改这俩函数呢,后来说不用改,就写了下面的
function handler() {
let timer = setTimeout(() => {
warning();
}, 5000)
api().then(data => {
clearTimeout(timer);
console.log('success');
})
}
12.上面的思路是对的,如果用原生的promise api来写怎么改进?(当时没想出来,说了用Promise.all或Promise.race。。其实应该用resolve、reject最好吧)
复盘了一下大概是这个思路:
function handler() {
return new Promise((resolve, reject) => {
api().then(() => {
clearTimeout(timer);
resolve();
}, () => {
clearTimeout(timer);
reject()
});
let timer = setTimeout(() => {
reject(warning());
}, 5000)
})
}
function api() {
return new Promise((resolve, reject) => {
console.log("pending");
reject();
})
}
function warning() {
console.log("warning");
}
handler().catch((err) => {});
上面这种方法我试了一下应该没问题,可惜面试的时候没想出来
13.Promise.all和Promise.race的话哪个更合适,区别是什么?
14.websocket介绍一下,实际情况下什么时候用websocket?
15.假设考虑一下降级方案,比如某些平台不支持websocket,怎么处理?
16.短轮询和长轮询的区别?
17.什么是虚拟DOM
18.对比更新的时候什么时候会只更新属性,什么情况下会销毁重建?
19.除了对比key以外,什么情况下会销毁重建?
其实想一下真的大部分是没有key的dom元素,但之前一直没想过这个问题,自己确实还是思考的太少了
回答到了比较key值,回答到了比较标签。具体如下:
可以看一下这篇博客,很全面:https://juejin.cn/post/7042221455618572296
总的来说基础的方法都能答出来,但是深度不够,感觉是要凉了,继续努力啦
#我的实习求职记录##拼多多##前端##软件开发2024笔面经##24届软开秋招面试经验大赏#