前端校招字节跳动面试 第四篇

832 阅读9分钟

面试官上来就问了一些比较简单的问题(除了自我介绍和项目经历)

1、块级元素和行内元素分别有哪些?

很简单,但是不容易答好,就跟问API一样,不过既然问了,还是要记一下:用分类法记住好

块级元素

行内元素

2、块级元素和行内元素的区别?

  • (1)行内元素会在一条直线上排列(默认宽度只与内容有关),都是同一行,水平方向排列。 块级元素各占据一行(默认宽度是他本身父容器的100%,与内容无关),垂直方向排列。块级元素从新行开始,结束接着一个断行。
  • (2)块级元素内可以包含行内元素,行内元素不能包含块级元素,只能包含文本或其他行内元素。
  • (3)块级元素和行内元素属性的不同,主要是盒模型属性上:行内元素设置width无效,height无效(可以设置line-height),margin上下无效,padding上下无效。

3、块级元素、行内元素的转换?

  • display:block;转换为块级
  • display:inline;转换为行内

4、行内元素如何设置宽高?

  • (1)display:block;
  • (2)display:inline-block;
  • (3)float:left;隐形的将行内元素进行了转化,相当于display:block;float:left;

5、js中如何判断数据的类型?

(1)typeof

缺陷:

1.不能判断变量具体的数据类型比如数组、正则、日期、对象,因为都会返回object,不过可以判断function,如果检测对象是正则表达式的时候,在Safari和Chrome中使用typeof的时候会错误的返回"function",其他的浏览器返回的是object.

2.判断null的时候返回的是一个object,这是js的一个缺陷,判断NaN的时候返回是number

**(2)instanceof **

可以用来检测这个变量是否为某种类型,返回的是布尔值,并且可以判断这个变量是否为某个函数的实例,它检测的是对象的原型

let num = 1
num instanceof Number // false

num = new Number(1)
num instanceof Number // true

明明都是num,而且都是1,只是因为第一个不是对象,是基本类型,所以直接返回false,而第二个是封装成对象,所以true。

这里要严格注意这个问题,有些说法是检测目标的__proto__与构造函数的prototype相同即返回true,这是不严谨的,检测的一定要是对象才行,如:

let num = 1
num.__proto__ === Number.prototype // true
num instanceof Number // false

num = new Number(1)
num.__proto__ === Number.prototype // true
num instanceof Number // true

num.__proto__ === (new Number(1)).__proto__ // true

instanceof只能通过true或者false来判断,不能直接看出来是什么类型

此外,instanceof还有另外一个缺点:如果一个页面上有多个框架,即有多个全局环境,那么我在a框架里定义一个Array,然后在b框架里去用instanceof去判断,那么该array的原型链上不可能找到b框架里的array,则会判断该array不是一个array。

(3)constructor

constructor是prototype对象上的属性,指向构造函数。根据实例对象寻找属性的顺序,若实例对象上没有实例属性或方法时,就去原型链上寻找,因此,实例对象也是能使用constructor属性的。

如果输出一个类型的实例的constructor,就如下所示:

console.log(new Number(123).constructor)
//ƒ Number() { [native code] }

可以看到它指向了Number的构造函数,因此,可以使用num.constructor==Number来判断一个变量是不是Number类型的。

(4)使用Object.prototype.toString.call(value) 方法去调用对象,得到对象的构造函数名。可以解决instanceof的跨框架问题,缺点是对用户自定义的类型,它只会返回[object Object]

6、盒子模型

参考立下flag)每日10道前端面试题-18 关于【盒模型】十问

7、如何实现三列布局?

三列布局,一般指两端固定宽度,中间宽度自适应的布局方式。 参考字节跳动:圣杯布局,有几种办法 当然,这个可以谈到grip,table

8、CSS实现三角形。(敲代码)不用多说

将一个div的宽度和高度设置为0,然后设置边框样式

.triangle{
    width: 0;
    height: 0;
    border-top: 50px solid black;
    border-right: 50px solid red;
    border-bottom: 50px solid green;
    border-left: 50px solid blue;
}

将一个div的border都设置成50px粗,并且不同颜色,结果如下图所示:

把边框宽度设置成50px,计算机处理时,在边框交接处,一边占用一半的面积。

将左右下边框设置成transparent,就可以画出一个三角形

.triangle{
    width: 0;
    height: 0;
    border-top: 50px solid black;
    border-right: 50px solid transparent;
    border-bottom: 50px solid transparent;
    border-left: 50px solid transparent;
}
/*下面代码更加简洁*/
.triangle{
    width: 0;
    height: 0;
    border: 50px solid transparent;
    border-top-color: black ;
}

就实现了三角形。

优化下:将下边框的长度设置为0,实现一个最小空间的三角形

上面产生的三角形,实质上占位还是一个正方形,所以我们应该将这个三角形占用的空间尽可能缩小。不设置下边框

  .triangle{
    width: 0;
    height: 0;
    border-top: 50px solid black;
    border-right: 50px solid transparent;
    border-left: 50px solid transparent;
}

9.设计一个简单的任务队列,要求分别在1,3,4秒后打印出”1“,”2“,”3“

 new Quene()
        .task(1000, () => {
            console.log(1)
        })
        .task(2000, () => {
            console.log(2)
        })
        .task(1000, () => {
            console.log(3)
        })
        .start()

    function Quene() { ... }

A:看这代码显然是链式调用,那就是Promise.then了

 function Quene() {
  this.quene = [];
}


Quene.prototype.task = function (time, callback) {
  this.quene.push({ time, callback });
  return this;
};

Quene.prototype.start = function () {
  const quene = this.quene;
  let result = Promise.resolve();

  quene.forEach((item) => {
    result = result.then(() => {
      return new Promise((resolve, reject) => {
        setTimeout(() => {
          resolve(item.callback());
        }, item.time);
      });
    });
  });

  return result;
};


new Quene()
  .task(1000, () => {
    console.log(1)
  })
  .task(2000, () => {
    console.log(2)
  })
  .task(1000, () => {
    console.log(3)
  })
  .start()

要是没有题目的限制,用async await超简单

async function one() {
    setTimeout(function() {
        console.log(1);
    }, 1000);}
async function two() {
    setTimeout(function() {
        console.log(2);
    }, 3000);}
async function three() {
    setTimeout(function() {
        console.log(3);
    }, 4000);}
async function run() {
    var p1 = await one();
    var p2 = await two();
    var p3 = await three();
}
run(); 

10、http的七层模型

SSL协议到底工作在OSI模型中的哪一层

SSL协议位于TCP/IP协议与各种应用层协议之间,为数据通讯提供安全支持。SSL协议可分为两层:

  1. SSL记录协议(SSL Record Protocol):它建立在可靠的传输协议(如TCP)之上,为高层协议提供数据封装、压缩、加密等基本功能的支持。
  2. SSL握手协议(SSL Handshake Protocol):它建立在SSL记录协议之上,用于在实际的数据传输开始前,通讯双方进行身份认证、协商加密算法、交换加密密钥等。

会话层的功能和表示层的功能正好和SSL记录协议和握手协议的功能一样,我想这两层协议就应该分别工作在这上面!

11.给定一个升序整数数组[0,1,2,4,5,7,13,15,16],找出其中连续出现的数字区间如下:

["0->2",”4->5“,"7","13","15->16"]

A:还算比较简单的算法题吧,还好当时做出来了,不然可能就止步于此。。也希望大家能谈点自己对这道题的解法

    function Arr(arr) {
        var len = arr.length,
            j,
            newArr = [],
            str = '';
        for (var i = 0; i < len; i++) {
            j = i;
            if (arr[i] + 1 === arr[j + 1]) {
                while (arr[j] + 1 === arr[j + 1]) {
                    str = '->' + arr[j + 1];
                    j++;
                }
                str = arr[i] + str;
                newArr.push(str)
                i = j
            } else {
                newArr.push(arr[i].toString())
            }
        }
        return newArr;
    }

12、xss和跨站伪造攻击防御

参考

WEB安全之-CSRF(跨站请求伪造)

web安全之XSS攻击原理及防范

13、类数组对象是什么?

1.定义

满足两个条件的对象就是类数组。

  • (1)有length属性,最好加上push方法
  • (2)属性要为索引属性

如下:

var arr = {
    "0": "a",
    "1": "b",
    "2": "c",
    length: 3
};

类数组并不能直接使用数组的方法,需要用call()或者apply()调用数组的方法。、

类似于这样


var obj = {
    "0": "a",
    "1": "b",
    "2": "c",
    length: 3
};
Array.prototype.join.call(obj,"+");    //"a+b+c"

2. 类数组转化为数组

第一种方法:

var obj = {
    "0": "a",
    "1": "b",
    "2": "c",
    length: 3
};

var b = [];
for (var i = 0; i < obj.length; i++){
    b.push(obj[i]);
}    //["a","b","c"];

第二种方法:


var obj = {
    "0": "a",
    "1": "b",
    "2": "c",
    length: 3
};

var

array = Array.prototype.slice.call(obj,0); //截取obj返回一个新数组

第三种方法,ES6中的方法,只要有length属性都可以应用此方法。

var obj = {
    "0": "a",
    "1": "b",
    "2": "c",
    length: 3
};

var array = Array.from(obj);

第四种方法:

var newArr = […obj]; //可以应用ES6的扩展运算符

15:、http的状态码


1xx 表示信息,服务器收到请求,需要请求者继续执行操作
100 Continue 信息型状态响应码表示目前为止一切正常, 客户端应该继续请求, 如果已完成请求则忽略
101 Switching Protocol(协议切换)状态码表示服务器应客户端升级协议的请求(Upgrade请求头)正在进行协议切换。

2xx 表示成功,操作被成功接收并处理
200 服务器成功处理了请求并提供请求的页面。
202 服务器已接受请求,但尚未处理。最终该请求可能会执行,也可能不执行。
204 服务器成功处理了请求,但没有返回任何内容。

3xx 表示重定向,需要进一步的操作以完成请求
301 表示客服端请求的文档在其他地方,新的URL地址在Location头中给出,浏览器应该自动访问新的URL。
302 临时重定向,类似于301,但新的URL应该被视为临时性的代替,而不是永久性的。
304 客户端有缓存的文档并发出一个条件性的请求。服务器告诉客户,原来缓存的文档还可以继续使用。

4xx 客户端错误,请求包含语法错误或无法完成请求
400 请求出现语法错误。
401 请求要求身份验证(未授权),对于需要登录的页面,服务器可能返回此响应。
403 服务器拒绝请求(禁止)。
404 服务器找不到请求的页面(未找到)。

5xx 服务器错误,服务器在处理请求的过程中发生了错误
500 服务器遇到错误,无法完成请求(服务器内部错误)。
501 服务器不具备完成请求的功能(尚未实施)。
503 服务器目前无法使用(超载或停机维护,服务器不可用)。
505 服务器不支持请求中所用的HTTP协议版本。

本文使用 mdnice 排版