前端面试常问问题(1)

312 阅读10分钟

1.http

1.1 什么是http

http: 超文本传输协议,是互联网上应用最为广泛的一种网络协议,是一个客户端和服务器端请求和应答的标准(TCP),
用于从WWW服务器传输超文本到本地浏览器的传输协议,它可以使浏览器更加高效,使网络传输减少。

1.2 一个完整的http请求过程

1.对www.baidu.com这个网址进行DNS域名解析,得到对应的IP地址
2.根据这个IP,找到对应的服务器,发起TCP的三次握手
3.建立TCP连接后发起HTTP请求
4.服务器响应HTTP请求,浏览器得到html代码
5.浏览器解析html代码,并请求html代码中的资源(如js、css图片等)(先得到html代码,才能去找这些资源)
6.浏览器对页面进行渲染呈现给用户

1.3 http的三次握手

三次握手协议指的是在发送数据的准备阶段,服务器端和客户端之间需要进行三次交互:
第一次握手:客户端发送syn包(syn=j)到服务器,并进入SYN_SEND状态,等待服务器确认;
第二次握手:服务器收到syn包,必须确认客户的syn(ack=j+1),同时自己也发送一个SYN包(syn=k),即SYN+ACK包,此时服务器进入SYN_RECV状态;
第三次握手:客户端收到服务器的SYN+ACK包,向服务器发送确认包ACK(ack=k+1),此包发送完毕,客户端和服务器进入ESTABLISHED状态,完成三次握手。连接建立后,客户端和服务器就可以开始进行数据传输了。

1.4 http状态码以及常用状态码

1xx:指示信息--表示请求已接收,继续处理。
2xx:成功--表示请求已被成功接收、理解、接受。
    200: 服务器成功接收了请求并进行了处理
    202:服务器成功接收了请求但是暂未进行处理
3xx:重定向--要完成请求必须进行更进一步的操作。
    301:客户端请求的资源已经永久移动到了别的位置,服务端会自动将该请求重定向到新的位置
4xx:客户端错误--请求有语法错误或请求无法实现。
    401:需要用户进行登录
    403:服务器接收到请求,但是拒绝进行处理
    404:访问的资源不存在
5xx:服务器端错误--服务器未能实现合法的请求。
    500:服务端代码错误
    503:服务器正在维护或访问过载,过一段时间可能恢复正常

1.5 http与https的区别

http的中文叫做超文本传输协议,它负责完成客户端到服务端的一系列操作,是专门用来传输注入HTML的超媒体文档等web内容的协议,它是基于传输层的TCP协议的应用层协议
https:https是基于安全套接字的http协议,也可以理解为是http+ssl/tls(数字证书)的组合
**http和https的区别:**
    *1 HTTP 的 URL 以 http:// 开头,而 HTTPS 的 URL 以 https:// 开头
    *2 HTTP 是不安全的,而 HTTPS 是安全的
    *3 HTTP 标准端口是 80 ,而 HTTPS 的标准端口是 443
    *4 HTTP无需认证证书,而https需要认证证书 

1.5.1 HTTPS工作原理

1.首先服务端给客户端传输证书,这个证书就是公钥,只是包含了很多的信息,比如说证书的办法机构,证书的过期时间
2.客户端进行证书的解析,比如说验证办法机构,过期时间,如果发现没有任何问题,就生成一个随机值(私钥),然后用证书
对这个私钥进行加密,并发送给服务端
3.服务端使用私钥将这个信息进行解密,得到客户端的私钥,然后客户端和服务端就可以通过这个私钥进行通信了
4.服务端将消息进行对称加密(简单来说就是讲消息和私钥进行混合,除非知道私钥否则服务进行解密),私钥正好只有客户
端和服务端知道,所以信息就比较安全了
5.服务端将进行对称加密后的消息进行传送
6.客户端使用私钥进行信息的解密
小结:https就是使用了非对称加密(一对公私钥进行加密解密)进行公钥传输,然后客户端通过公钥加密将自己的私钥发给
服务端,以后就可以使用这个私钥进行消息的收发了

1.6 常用的HTTP方法有哪些

GET 从服务器获得资源

POST 客户端向服务器提交资源

PUT 修改服务器相关资源  (已经很少用)

DELETE 删除服务器相关资源   (已经很少用)

1.7 浏览器的渲染过程

解析HTML,生成DOM树,解析CSS生产CSSOM
根据生成的DOM和CSSOM构建渲染树Render tree
根据渲染树,计算每个节点在屏幕上的位置,尺寸等信息。
将渲染树绘制到屏幕上
查询网址:[https://www.jianshu.com/p/b6b42fd3f80e]()

2. html,css,js常问知识点

2.1 html5新增标签,css3新增

html: header ,footer,artical,section,aside,time,progress,audio,video等
css: 过渡,转换,动画,阴影,圆角,弹性布局,媒体查询等

2.2 web性能优化方法

1.使用矢量图标替换图片图标
2.使用精灵图片
3.对大图片进行压缩
4.减少对dom的操作
5.压缩并合并js,css文件
6.图片进行懒加载

2.3垂直居中的方法

1.行内元素
    1.设置行高 line-height:100px
    2.display:table(父级) display:table-cell;vertical-align:middle;(子级)
    3.绝对定位的方式 display:absolute;
    4.弹性布局的方式 display:inline-flex;
2.块级元素
    1.position:absolute; top/right/bottom/left:0;margin:auto;
    2.position:absolute;top:50%;left:50%;margin:-50px 0 0 -50px;
    3.display:flex;

2.4 同源策略与跨域

1.同源策略
同源策略是浏览器的一个安全功能,不同源的客户端脚本在没有明确授权的情况下,不能读写对方资源。所以xyz.com下
的js脚本采用ajax读取abc.com里面的文件数据是会被拒绝的。
同源策略限制了从同一个源加载的文档或脚本如何与来自另一个源的资源进行交互。这是一个用于隔离潜在恶意文件的重
要安全机制。
2.一个源的定义
如果两个页面的协议,端口(如果有指定)和域名都相同,则两个页面具有相同的源。
3.jsonp跨域(封装函数代码如下)
jsonp({
        url: 'http://localhost:3000/',
        data: '',
        success: function (data) {
            console.log(7777);
        }
    });
function jsonp(option) {
     // 0. 将用户通过对象的命名空间传递进来的函数挂载到全局
    var callbackName = 'itlike_' + Math.random().toString().substr(2)+ Math.random().toString().substr(2);
    window[callbackName] = function (data) {
        option.success(data);
        // 删除script标签
        document.body.removeChild(script);
    };
    // 1. 处理url的拼接
    option.url = option.url + '?callback=' + callbackName;
    // 2. 创建script标签
    var script = document.createElement('script');
    script.src = option.url;
    document.body.appendChild(script);
}

2.5 json转formdata与formdata转json

1.json转formdata
const formData = new FormData();
Object.keys(params).forEach((key) => {
formData.append(key, params[key]);
});
2.formdata转json
var jsonData = {};
formData.forEach((value, key) => jsonData[key] = value);

2.6 aiax请求的过程与封装

(function (window) {
    function AjaxTool() {}
    AjaxTool.ajaxRequest = function (params, successCallBack, errorCallBack) {
        // 0. 获取参数
        var requestType = params['requestType'] || 'get';
        var url = params['url'];
        var paramObj = params['paramObj'];
        var timeout = params['timeout'];

        // 1.创建XMLHttpRequest对象 (找到一个电话)
        var xhr;
        if (window.XMLHttpRequest) {
            xhr = new XMLHttpRequest();
        } else {
            xhr = new ActiveXObject('Microsoft.XMLHTTP');
        }

        // 2. 判断请求方式
        if(requestType.toLowerCase() === 'get'){
            var codeURI = encodeURI(url + '?' + getStrWithObject(paramObj));
            xhr.open('get', codeURI, true);
            xhr.send();
        }else if(requestType.toLowerCase() === 'post' ){
            // 请求体
            var codeParam = encodeURI(getStrWithObject(paramObj));
            xhr.open('post', url, true);
            xhr.setRequestHeader('Content-Type', 'application/x-www-from-urlencoded');
            xhr.send(codeParam);
        }

        // 3. 监听服务器的响应 (等待电话拨通)
        xhr.onreadystatechange = function () {
            // 4. 处理响应的数据 (对方说话)
            if (xhr.readyState === 4) {
                // 代表服务器已经给了响应, 不代表响应成功
                if (xhr.status === 200) {
                    successCallBack(xhr);
                    // 清除请求定时器
                    clearTimeout(timer);
                } else {
                    errorCallBack();
                }
            }
        };

        // 5. 控制请求的时间
        var timer;
        if (timeout > 0) {
            timer = setTimeout(function () {
                // 取消ajax请求
                xhr.abort();
            }, timeout);
        }
    };

    /**
     * 返回一个随机数
     */
    function getRandomStr() {
        return Math.random() + (new Date().getTime())
    }

    /**
     * 把对象转成字符串
     */
    function getStrWithObject(paramObj) {
        var rArr = [];
        for (var key in paramObj) {
            var str = key + '=' + paramObj[key];
            rArr.push(str);
        }
        rArr.push('random=' + getRandomStr());
        return rArr.join('&');
    }

    window.AjaxTool = AjaxTool;
})(window);

2.7 flex的相关知识

1.flex的基础属性,这个经常会问;尽量全部记住 2.flex:1;是1 1 0%的缩写,一般用于让所有弹性盒模型对象的子元素都有相同的长度 3.flex:0;是1 1 auto的缩写;

2.8 常用数组去重的方法(记住三四种即可,一定要记住es6中set去重方法)

//1.利用for嵌套for,然后splice去重
function unique(arr){            
        for(var i=0; i<arr.length; i++){
            for(var j=i+1; j<arr.length; j++){
                if(arr[i]==arr[j]){         //第一个等同于第二个,splice方法删除第二个
                    arr.splice(j,1);
                    j--;
                }
            }
        }
return arr;
}
var arr = [1,1,'true','true',true,true,15,15,false,false, undefined,undefined, null,null, NaN, NaN,'NaN', 0, 0, 'a', 'a',{},{}];
    console.log(unique(arr))
    //[1, "true", 15, false, undefined, NaN, NaN, "NaN", "a", {…}, {…}]     //NaN和{}没有去重,两个null直接消失了
//2.利用indexOf去重
function unique(arr) {
    if (!Array.isArray(arr)) {
        console.log('type error!')
        return
    }
    var array = [];
    for (var i = 0; i < arr.length; i++) {
        if (array .indexOf(arr[i]) === -1) {
            array .push(arr[i])
        }
    }
    return array;
}
var arr = [1,1,'true','true',true,true,15,15,false,false, undefined,undefined, null,null, NaN, NaN,'NaN', 0, 0, 'a', 'a',{},{}];
console.log(unique(arr))
   // [1, "true", true, 15, false, undefined, null, NaN, NaN, "NaN", 0, "a", {…}, {…}]  //NaN、{}没有去重
3.利用includes去重
function unique(arr) {
    if (!Array.isArray(arr)) {
        console.log('type error!')
        return
    }
    var array =[];
    for(var i = 0; i < arr.length; i++) {
            if( !array.includes( arr[i]) ) {//includes 检测数组是否有某个值
                    array.push(arr[i]);
              }
    }
    return array
}
var arr = [1,1,'true','true',true,true,15,15,false,false, undefined,undefined, null,null, NaN, NaN,'NaN', 0, 0, 'a', 'a',{},{}];
    console.log(unique(arr))
    //[1, "true", true, 15, false, undefined, null, NaN, "NaN", 0, "a", {…}, {…}]     //{}没有去重
4.利用过滤器filter去重
function unique(arr) {
  return arr.filter(function(item, index, arr) {
    //当前元素,在原始数组中的第一个索引==当前索引值,否则返回当前元素
    return arr.indexOf(item, 0) === index;
  });
}
    var arr = [1,1,'true','true',true,true,15,15,false,false, undefined,undefined, null,null, NaN, NaN,'NaN', 0, 0, 'a', 'a',{},{}];
        console.log(unique(arr))
//[1, "true", true, 15, false, undefined, null, "NaN", 0, "a", {…}, {…}]
5.利用es6中set去重
function unique (arr) {
  return Array.from(new Set(arr))
}
var arr = [1,1,'true','true',true,true,15,15,false,false, undefined,undefined, null,null, NaN, NaN,'NaN', 0, 0, 'a', 'a',{},{}];
console.log(unique(arr))
 //[1, "true", true, 15, false, undefined, null, NaN, "NaN", 0, "a", {}, {}]
6.利用[...new Set(arr)] 
[...new Set(arr)] 
//代码就是这么少----(其实,严格来说并不算是一种,相对于上一种方法来说只是简化了代码)

2.9 git常用命令

git clone:  从远程仓库克隆一个版本库到本地。
git init:初始化项目所在目录,初始化后会在当前目录下出现一个名为 .git 的目录。
git status:查看本地仓库的状态。
git branch:列出本地的所有分支,当前所在分支以 "*" 标出
git checkout:检出命令,用于创建、切换分支等。
git add:把要提交的文件的信息添加到暂存区中。
git commit:将暂存区中的文件提交到本地仓库中。
git merge:合并分支。
git pull:从远程仓库获取最新版本。
git push:把本地仓库的提交推送到远程仓库。
git stash:暂存当前正在进行的工作。
git pop:恢复暂存信息。

2.10 es6相关

1.let,const与var的区别
2.对象或者数组的解析结构
3.延展操作符(也叫三点运算符)
4.模板字符串替代字符串拼接
5.箭头函数(this指向)
6.promise用法