中软国际笔面试题

[toc]

笔试

1.HTML、CSS、js作用是什么?

Html: 超文本标记语言 主要用来做页面结构划分
CSS: 层叠样式表 主要用来做页面的样式的渲染
Js: javascript 主要用来实现页面的交互行为效果

2. var arr=[1,2,3,”1”,1,2,”a”,”b”] var brr=[1,2,”b”] 输出[3,”1’,”a”] 注:arr先去重

  1. var arr=[1,2,3,"1",1,2,"a","b"];
  2. var brr=[1,2,"b"];
  3. var result = [];
  4. // for (var i = 0; i < arr.length; i ++) {
  5. // if (brr.indexOf(arr[i]) === -1) {
  6. // result.push(arr[i]);
  7. // }
  8. // }
  9. var uniqueArr = [];
  10. for (var i = 0; i < arr.length; i++) {
  11. if (uniqueArr.indexOf(arr[i]) === -1) {
  12. uniqueArr.push(arr[i]);
  13. if (brr.indexOf(arr[i]) === -1) {
  14. result.push(arr[i]);
  15. }
  16. }
  17. }

3.写出axios和ajax的区别

传统 Ajax 指的是 XMLHttpRequest(XHR), 最早出现的发送后端请求技术,隶属于原始js中,核心使用XMLHttpRequest对象,多个请求之间如果有先后关系的话,就会出现回调地狱(此处可以再介绍一下回调地狱,以及解决回调地狱的方法)。

axios 是一个基于Promise 用于浏览器和 nodejs 的 HTTP 客户端,本质上也是对原生XHR的封装,只不过它是Promise的实现版本,符合最新的ES规范,它本身具有以下特征:

  1. 从浏览器中创建 XMLHttpRequest
  2. 支持 Promise API
  3. 客户端支持防止CSRF
  4. 提供了一些并发请求的接口(重要,方便了很多的操作)
  5. 从 node.js 创建 http 请求
  6. 拦截请求和响应
  7. 转换请求和响应数据
  8. 取消请求
  9. 自动转换JSON数据

防止CSRF:就是让你的每个请求都带一个从cookie中拿到的key, 根据浏览器同源策略,假冒的网站是拿不到你cookie中得key的,这样,后台就可以轻松辨别出这个请求是否是用户在假冒网站上的误导输入,从而采取正确的策略。

还有一个es6里面出现的网络请求方案——fetch

fetch号称是AJAX的替代品,使用了ES6中的promise对象。Fetch是基于promise设计的。Fetch的代码结构比起ajax简单多了,参数有点像jQuery的ajax。但是,一定记住fetch不是ajax的进一步封装,而是原生js,没有使用XMLHttpRequest对象。
我认为的fetch的优点是:

  1. 语法简洁,更加语义化
  2. 基于标准 Promise 实现,支持 async/await
  3. 同构方便,使用 isomorphic-fetch
  4. 更加底层,提供的API丰富(request, response)
    5 .脱离了XHR,是ES规范里新的实现方式

fetch是一个低层次的API,你可以把它考虑成原生的XHR,所以使用起来并不是那么舒服,需要进行封装。
例如:

  1. 1fetch只对网络请求报错,对400500都当做成功的请求,服务器返回 400500 错误码时并不会 reject,只有网络错误这些导致请求不能完成时,fetch 才会被 reject
  2. 2fetch默认不会带cookie,需要添加配置项: fetch(url, {credentials: 'include'})
  3. 3fetch不支持abort,不支持超时控制,使用setTimeoutPromise.reject的实现的超时控制并不能阻止请求过程继续在后台运行,造成了流量的浪费
  4. 4fetch没有办法原生监测请求的进度,而XHR可以

总结:axios既提供了并发的封装,也没有fetch的各种问题,而且体积也较小,当之无愧现在最应该选用的请求的方式。

4.SCSS可以用什么代替?

scss 是一种css扩展语言,所以肯定能用css实现。
其次还可以用less,sass等css预处理语言代替

sass和scss的区别在于扩展名不同,部分语法不同。
scss是sass的一个升级版本,所以scss兼容了所有sass之前的功能,又有些新增的功能,包括能做运算、写函数啥的

5.简述VUE的生命周期

vue生命周期主要分为: 创建前后,挂载前后,更新前后,销毁前后

创建前后的钩子函数为beforeCreate 和created,在这两个生命周期之间,进行初始化事件,进行数据的检测,可以看到在created的时候数据已经和data属性进行绑定(放在data中的属性当值放生变化的同时,视图也会改变),这个时候还没有el选项

挂载前后的钩子函数为beforeMount和 mount

在created钩子函数和beforeMount钩子函数之间,会判断对象是否有el选项,如果有的话就继续向下编译,如果没有el选项,则停止编译,也就意味着停止了生命周期。

在beforeMount和mounted之间的生命周期之间,给vue私立对象添加$el成员,并且会替换掉挂载的dom元素。

更新前后的钩子函数为beforeUpdate和updated,当数据发生变化时,会触发对应组件的重新渲染,先后会调用这两个钩子函数,区别在于beforeUpdate发生在数据改变时,updated发生在视图层改变之后

销毁前后的钩子函数为beforeDestory和destoryed,beforeDestroy 是在实例被销毁之前调用,在这一步,实例仍然完全可以调用。
destroyed 函数在实例被销毁之后调用,此时 vue 实例指示的所有东西都会解绑,所有的事件监听器会被移除,所有的子实例也会被销毁。

6.写出es6都有哪些新特性

  1. 新增了变量声明的方式
  2. 箭头函数
  3. 对象的defineProperty方法
  4. 类的概念
  5. 解构赋值
  6. promise异步处理方案
  7. ajax的接口fetch
  8. 迭代器api
  9. 代理Proxy

以上接口中哪个熟悉详细的介绍一下,最好所有的都进行描述

7.组件有多少种传参方式?

vue中组件传参方式有:

  1. prop
  2. 父组件传递数据给子组件时,可以通过特性传递。
  3. 推荐使用这种方式进行父->子通信。
  4. $emit
  5. 子组件传递数据给父组件时,触发事件,从而抛出数据。
  6. 推荐使用这种方式进行子->父通信。
  7. v-model
  8. .sync
  9. $attrs
  10. 祖先组件传递数据给子孙组件时,可以利用$attrs传递。
  11. demo或小型项目可以使用$attrs进行数据传递,中大型项目不推荐,数据流会变的难于理解。
  12. $attrs的真正目的是撰写基础组件,将非Prop特性赋予某些DOM元素。
  13. $listeners
  14. 可以在子孙组件中执行祖先组件的函数,从而实现数据传递。
  15. demo或小型项目可以使用$listeners进行数据传递,中大型项目不推荐,数据流会变的难于理解。
  16. $listeners的真正目的是将所有的事件监听器指向这个组件的某个特定的子元素。
  17. $root
  18. 可以在子组件中访问根实例的数据。
  19. 对于 demo 或非常小型的有少量组件的应用来说这是很方便的。中大型项目不适用。会使应用难于调试和理解。
  20. $parent
  21. 可以在子组件中访问父实例的数据。
  22. 对于 demo 或非常小型的有少量组件的应用来说这是很方便的。中大型项目不适用。会使应用难于调试和理解。
  23. $children
  24. 可以在父组件中访问子实例的数据。
  25. 对于 demo 或非常小型的有少量组件的应用来说这是很方便的。中大型项目不适用。会使应用难于调试和理解。
  26. ref
  27. 可以在父组件中访问子实例的数据。
  28. $refs 只会在组件渲染完成之后生效,并且它们不是响应式的,适用于demo或小型项目。
  29. provide & inject
  30. 祖先组件提供数据(provide),子孙组件按需注入(inject)。
  31. 会将组件的阻止方式,耦合在一起,从而使组件重构困难,难以维护。不推荐在中大型项目中使用,适用于一些小组件的编写。
  32. eventBus(事件总线)
  33. Vue.prototype.$bus = new Vue();
  34. Vue.component('cmp-a', {
  35. data () {
  36. return {
  37. a: 'a'
  38. }
  39. },
  40. methods: {
  41. onClick () {
  42. this.$bus.$on('click', this.a)
  43. }
  44. },
  45. template: `
  46. <div>
  47. <button @click="onClick">点击</button>
  48. </div>
  49. `,
  50. })
  51. Vue.component('cmp-a', {
  52. mounted () {
  53. this.$bus.$on('click', data => {
  54. console.log(data);
  55. })
  56. },
  57. template: `
  58. <div>b</div>
  59. `,
  60. })
  61. 非父子组件通信时,可以使用这种方法,但仅针对于小型项目。中大型项目使用时,会造成代码混乱不易维护。
  62. Vuex

8.写出VUEX中,State,mutation和action的联系

state 是真正的存储数据的属性,在vuex中只有mutation才能可以直接操作state,Vuex 中的 mutation 非常类似于事件:每个 mutation 都有一个字符串的 事件类型 (type) 和 一个 回调函数 (handler)。这个回调函数就是我们实际进行状态更改的地方,并且它会接受 state 作为第一个参数,要唤醒一个mutation handler我们需要相应的type调用store.commit(type),如果mutation的handler需要传递参数,则在commit的第二个参数开始是handler的值参

Action 类似于 mutation,不同在于:

  • Action 提交的是 mutation,而不是直接变更状态。
  • Action 可以包含任意异步操作。 而mutation 不能(mutation做异步操作的时候,检测不到实时的状态改变)

9.写出setTimeout,SetInterval和requestAnimationFrame的区别

  • setTimeout 延迟执行回调函数,只执行一次
  • setInterval 每隔一段时间执行一次回调函数
  • requestAnimationFrame 下一次页面更新的时候执行回调函数 执行一次 如果页面更新的频率是60hz/秒 那么等同于setTimeout(fn, 1000 / 60);

10.什么是事件委托?

事件委托是指将事件不直接绑定在自己的身上,而是绑定在父元素身上,他的原理是事件冒泡,当触发子元素的指定事件的时候,也会触发父元素的相同的事件,区分哪个元素出发的事件接口是事件源对象身上的target属性,代表的是出发事件目标元素。做事件委托的时候要注意的是mouseenter mouseleave 事件不可以做事件委托,因为这两个事件不会触发是事件冒泡。

面试

1.什么是优雅降级和渐进增强?

优雅降级是指:向下兼容。 一开始针对高版本浏览器构建页面,先完善所有功能,然后针对低版本浏览器进行调整完善

渐进增强是指:向上兼容。一开始就针对低版本浏览器进行构建页面,满足最基本的功能要求,然后再针对高级浏览器进行效果,交互,追加各种功能以达到更好用户体验。

2.同源策略是什么?

同源策略是浏览器的一种安全机制,同源是指协议域名端口号都相同,该机制是说一般来说只有在同源下的网络交互才被认可,不同源的网络交互在响应的过程中浏览器会阻碍

3.浏览器是如何渲染页面的?

浏览器的渲染引擎会按照html 和css代码一行一行的绘制页面,绘制之前浏览器会先解析html和css代码

  1. 解析dom元素生成dom树:浏览器会对内核进行一步一步的检索,首先识别html代码 他会把你的html代码挂载到树形结构上,形成一个DOM树。dom树会遵循深度优先原则(一条枝干走完了之后才会形成下一个枝干) 生成dom树的过程叫做dom节点的解析。所有dom的加载完一定在dom解析完毕之后。即加载和解析是异步发生的。
  2. 解析css代码 生成css树:类似于dom树 与dom树是一一对应的 css树就是系统根据css代码挂在树上
  3. css树 + dom树组成一个新的树 叫做renderTree 即渲染树, 渲染树是页面开始绘制的前提

4.如何解决跨域问题?

跨域问题又分为客户端与服务器的跨域,客户端与客户端的跨域

  1. 客户端和服务器端的跨域解决方案:
  2. 1. 服务器代理中转
  3. webpack: devServer: 做服务器代理的接口
  4. nginx: 服务器代理
  5. 2. CORS跨域: Cross origin resource sharing 统一资源共享
  6. 请求分类:
  7. 1 简单请求
  8. a. 请求方式只能是 get / post / head
  9. b. 请求头字段
  10. Access-Language
  11. Content-Type: 值只能为
  12. application/x-www-form-urlencoded
  13. mutipart/form-data
  14. text/plain
  15. "Access-Control-Allow-Origin": "http://localhost:5500",
  16. 2 非简单请求
  17. "Access-Control-Allow-Origin": "*",
  18. "Access-Control-Allow-Methods": "GET,PUT",
  19. "Access-Control-Allow-Headers": "x-requested-with , content-type, token",
  20. 3. jsonp
  21. json and padding
  22. {}/[]/''
  23. jquery中提出的一种跨域的解决方案
  24. 原理是: script标签身上的src 这个属性是不受同源策略限制的
  25. put / head / delete / options
  26. 客户端和客户端的跨域:
  27. window.postMessage(要传递的数据, 允许拿到这个数据的源)
  28. h5之前的解决方案:
  29. 父窗口请求子窗口数据 iframe + window.name
  30. 子窗口请求父窗口的数据 iframe + location

5.如何用jQuery给一个标签添加一个属性?

  1. $(selector).attr(key, value);
  2. $(selector).prop(key, value);
  3. // 最好把这两个方法的区别讲述一下

6.怎样让一个元素居中?

块级元素水平垂直居中方案

  1. 通过定位实现水平垂直居中
  1. /* 第一种*/
  2. div {
  3. position: absolute;
  4. left: 50%;
  5. top: 50%;
  6. transform: translate(-50%, -50%);
  7. }
  8. /* 第二种 */
  9. div {
  10. position: absolute;
  11. left: 0;
  12. top: 0;
  13. right: 0;
  14. bottom: 0;
  15. margin: auto auto;
  16. }
  1. 弹性布局
  1. .father {
  2. display: flex;
  3. justify-content: center;
  4. align-items: center;
  5. }

7.描述一下路由的功能

路由的作用主要是分组转发,他的出现是单页面应用之间的切换,因为是单页应用,路由的核心作用就是告诉代码,根据当前的url,应该渲染哪个组件。

8.试说说防抖和节流

防抖:

当持续触发事件时,一定时间段内没有再触发事件,事件处理函数才会执行一次,如果设定时间到来之前,又触发了事件,就重新开始延时。也就是说当一个用户一直触发这个函数,且每次触发函数的间隔小于既定时间,那么防抖的情况下只会执行一次。

  1. function debounce(fn, wait) {
  2. var timeout = null; //定义一个定时器
  3. return function() {
  4. if(timeout !== null)
  5. clearTimeout(timeout); //清除这个定时器
  6. timeout = setTimeout(fn, wait);
  7. }
  8. }
  9. // 处理函数
  10. function handle() {
  11. console.log(Math.random());
  12. }
  13. // 滚动事件
  14. window.addEventListener('scroll', debounce(handle, 1000));

节流:

当持续触发事件时,保证在一定时间内只调用一次事件处理函数,意思就是说,假设一个用户一直触发这个函数,且每次触发小于既定值,函数节流会每隔这个时间调用一次

  1. var throttle = function(func, delay) {
  2. var timer = null;
  3. var startTime = Date.now(); //设置开始时间
  4. return function() {
  5. var curTime = Date.now();
  6. var remaining = delay - (curTime - startTime); //剩余时间
  7. var context = this;
  8. var args = arguments;
  9. clearTimeout(timer);
  10. if (remaining <= 0) { // 第一次触发立即执行
  11. func.apply(context, args);
  12. startTime = Date.now();
  13. } else {
  14. timer = setTimeout(func, remaining); //取消当前计数器并计算新的remaining
  15. }
  16. }
  17. }
  18. function handle() {
  19. console.log(Math.random());
  20. }
  21. window.addEventListener('scroll', throttle(handle, 1000));

用一句话总结防抖和节流的区别:防抖是将多次执行变为最后一次执行,节流是将多次执行变为每隔一段时间执行
实现函数节流我们主要有两种方法:时间戳和定时器

9.ajax发送请求出现乱码怎么解决?

设置请求头中的编码类型contentType属性后面加上字符集

10.虚线边框

  1. border: 1px dashed #000;

11.怎么实现在jQuery中找到所在的同辈元素?

  1. $(selector).siblings()

12. 简述h5中新增的canvas,svg,audio标签的作用

canvas和svg是用于绘图的标签, canvas 绘图技术主要是通过js脚本语言进行绘制,而svg主要是html 和css配合进行绘制,一般我们会用canvas绘制大型的图表,游戏等,而用svg绘制一些小图标,svg绘制出来的是一个矢量图而canvas绘制出来的是位图

audio是音频标签,主要用来做一些音频播放的效果,js中还针对audio专门有一些控制播放的接口供我们使用,audio标签在使用的时候如果设置自动播放在谷歌浏览器上面会又报错,解决这个问题可以等待音频资源加载过来之后通过js控制播放

13. 简述如何通过css实现响应式布局的方式

通过媒体查询,相对单位,以及弹性布局的方式可以实现响应式布局

通过媒体查询和弹性布局为不同宽度的设备设置不同的布局样式。
使用相对单位,为不同的设备设置不同的大小

14. 什么是事件流

事件流也就是事件的流式,举个简单的例子,鼠标的事件,鼠标事件中有很多例如鼠标按下(mousedown),抬起(mouseup),移动(mousemove),移入(mouseenter,mouseover),移出(mouseleave,mouseout)等,当我使用鼠标执行一个行为之后,他可能触发的事件有多个,那么他们的先后顺序就是事件流

15. 简述DOM, HTML DOM的区别跟联系

DOM 是指文档对象模型,是在js中对于整个页面进行操作的模块,该模块包含了文件里面所有的内容,主要用于在js中操作页面渲染功能

HTML DOM 是在js中html的一些标签进行对象化了,如img标签可以用Image对象创建等 一般用于操作对象的属性

HTML DOM 属于DOM 的一部分