阅读 8708

字节跳动web前端面试经历

都说今年是互联网的寒冬,由于个人原因想要换个地方工作,所以在某boss上投递了简历,当天就收到诸多boss的消息,让我发送简历,其中就包括我想去的宇宙条。宇宙条的效率是真的很高,收到简历后没多久就打电话过来约面试时间,由于本人是异地,故只能接受电话/视频面试。很快确定了面试时间和方式,宇宙条的面试可安排在周末,由此便可知道其“加班定律”。我面试的岗位是web前端开发工程师岗,坐标北京。

面试铁律

自我介绍,基本上这是开启激战的导火索。顺便一提,宇宙条的视频面试是在牛客网上,可进行编码,视频,语音,文字沟通。面试官可以实时看到应聘者当前页面的内容和操作。

基础题

1.display的取值和各种值的区别?

2.相邻的两个inline-block节点为什么会出现间隔,该如何解决?

3.用过nodejs中的EventEmitter吗?详细讲讲。

4.前端性能优化有哪些?

5.讲简历中提到的一个项目,并且讲解服务端渲染和前端渲染的优缺点?为什么你的项目会选择服务端渲染?

6.讲讲CSRF。

7.ts和js的区别,为什么要选择使用ts?

算法题

找出数组中和为给定值的两个元素,如:[1, 2, 3, 4, 5]中找出和为6的两个元素。

题目很清晰,也很容易理解,相信很多小伙伴看到这个题都能直观地用“冒泡排序”的方法解决,但是冒泡排序的时间复杂度明显不是我们想要的结果,我把我能够想到的几种方法由易到难记录下来:

冒泡排序的方式

function getNum(arr, sum) {
    if (!Array.isArray(arr)) return null;

    for (var i = 0; i < arr.length - 1; i++) {
        if (arr[i] > sum) continue;

        for (var j = 0; j < arr.length; j++) {
            if (arr[j] > sum) continue;

            if (arr[i] + arr[j] == sum) return [arr[i], arr[j]];
        }
    }

    return null;
}
复制代码

这种解法很容易想到,也很容易理解,我们不多过多的讲解,接下来分享一种上述解法的优化版。

查找的方式

最终的结果是要找到和为sum的两个数,那么我们可以转换一种思路:默认第一个num1数已经存在,那么第二个数就是sum - num1,这就转换为从数组中查找的问题了。虽然和第一种方法很像,但是在有序数列中进行查找明显要快于逐个比较。

function getNum(arr, sum) {
    if (!Array.isArray(arr)) return null;

    arr.sort();

    for (var i = 0; i < arr.length - 1; i++) {
        if (arr[i] > sum) continue;

        var restNum = sum - arr[i];

        // 考虑下为什么要 > i
        if (arr.indexOf(restNum) > i) return [arr[i], restNum];
    }

    return null;
}
复制代码

这种解法的前提是需要对数组进行排序(快排),故时间复杂度为O(nlogn),二分查找的时间复杂度为O(log2n),最坏的情况是遍历了整个数组,即时间复杂度为O(n),那么整体的时间复杂度为O(nlog2n),效果上要优于冒泡排序的方式。

快排方式

同样需要对数组进行排序(升序),我们知道排序后的数组必然是左边的数不会超过右边的数,因此我们可以把左边的数和右边的数的和作为基准值来和目标值比较,如果该值小于目标值,那么代表两个加数的值不够大,右边的值已经到达顶峰了,那么就从左边取下一个值相加和目标值比较,如果该值比目标值大,那么表示右边的值太大了,需要获取一个小一点的加数,这时需要从右边取倒数第二个数相加后比较,如果此时的值和目标值相等,恭喜你,我的小乖乖,原来你俩在这里!说了这么多感觉还是一头雾水的同学直接看代码吧,毕竟我们都是同一类猿:-)

function getNum(arr, sum) {
    if (!Array.isArray(arr)) return null;

    arr.sort();

    for (var i = 0, j = arr.length - 1; i < j;) {
        if (arr[i] + arr[j] < sum) i++;

        else if (arr[i] + arr[j] > sum) j--;

        else return [arr[i], arr[j]];
    }

    return null;
}
复制代码

这种方法我是受到了快速排序的启发,所以命名为快速排序的方式,它是目前为止我能想到效率最高的解决方案,时间复杂度为O(nlogn)。如果需求是找出所有对组合,只要控制退出条件即可,难度不大故不做讨论。

总结

首先说下最终的结果吧,跪了!不得不说宇宙条的效率很高,从简历采集到最终出结果全程可以和HR进行交流,面试前夕也会电话确认,面试结束后会有一个面试评价,好像是每轮面试都有,网上匿名填写,面试的结果在当天或是1-2个工作日会通过邮件的形式发送给你。

再说说自己吧,面试之前就没有备足功课,一方面,当前的工作强度较大,天天加班的前提下抽出时间去学习是件奢侈的事情,只能在工作中边做事情边积累。另一方面,自己之前面试结果都很满意,所以有点飘了。导致这次面试自我介绍都有点结结巴巴,后面的问题也是很难用语言准确表达出来,提到这里我个人感觉面试官还是很和蔼的,看到我的处境说写出来就可以了。

基础题看上去都很简单,所以我就没有写答案,有兴趣的小伙伴可以留言你自己的答案。本人虽然是计算机专业但是算法一直不算是我的强项,本次面试最让我伤心的就是算法题,面试完成后一直都在考虑具体的解法,在时间的发酵下总算有了一点点收货,还是值得庆幸的事情。

接下来一段时间还是要系统地总结和学习,不管是不是为了面试,既然选择了这一行就应该努力充实自己,等自己变得足够强的时候,自然是别人认可你的时候!最后也预祝和我一样想要换工作的小伙伴都能收到心仪公司的offer:-)。