1、- 面试题 -1 vuex 的五个状态VueX 是一个专门为状态 (你可以理解成vueVue.js 应用设计的状态管理架构,统一管理和维护各个组件里的某些data ) 。vue组件的可变化Vue 有五个核心概念,state, getters, mutations, actions, modulesstate = 基本数据=datagetters = 从基本数据派生的数据=computedmutations =提交更改数据的方法,同步 !=methodsactions = 像一个装饰器,包裹mutations ,使之可以 异步 。modules = 模块化 Vuex。2 vue 周期(钩子函数
2、)created 可获取数据Mounted可操作DOMVue 实例有一个完整的生命周期,也就是从开始创建、初始化数据、编译模板、挂载染 更新 渲染、销毁等一系列过程,我们称这是Vue 的生命周期。通俗说就是销毁的过程,就是生命周期。分为三个阶段:初始化、运行中、销毁。VueDom 、渲实例从创建到beforeCreate :实例、组件通过new Vue() 创建出来之后会初始化事件和生命周期,然后就会执行 beforeCreate 钩子函数,这个时候,数据还没有挂载呢,只是一个空壳,无法访问到数据和真实的 dom ,一般不做操作Created:挂载数据,绑定事件等等,然后执行可以更改数据,在这
3、里更改数据不会触发updatedcreated 函数,这个时候已经可以使用到数据,也函数,在这里可以在渲染前倒数第二次更改数据的机会,不会触发其他的钩子函数,一般可以在这里做初始数据的获取beforeMount :接下来开始找实例或者组件对应的模板,编译模板为虚拟dom 放入到 render数中准备渲染,然后执行beforeMount钩子函数,在这个函数中虚拟dom 已经创建完成,马上就要渲染 ,在这里也可以更改数据,不会触发updated ,在这里可以在渲染前最后一次更改数据的机会,不会触发其他的钩子函数,一般可以在这里做初始数据的获取函Mounted :接下来开始render ,渲染出真实
4、dom ,然后执行mounted经出现在页面中,数据、真实 dom 都已经处理好了,事件都已经挂载好了,等事情 .钩子函数,此时,组件已可以在这里操作真实dombeforeUpdate :当组件或实例的数据更改之后, 会立即执行 beforeUpdate ,然后 vue 的虚拟 dom 机制会重新构建虚拟 dom 与上一次的虚拟 dom 树利用 diff 算法进行对比之后重新渲染, 一般不做什么事儿Updated:当更新完成后,执行updated ,数据已经更改完成,dom也重新render完成,可以操作更新后的虚拟dombeforeDestroy:当经过某种途径调用$destroy方法后,
5、立即执行beforeDestroy ,一般在这里做一些善后工作,例如清除计时器、清除非指令绑定的事件等等Destroyed :组件的数据绑定、监听.去掉后只剩下dom空壳,这个时候,执行destroyed,在这里做善后工作也可以钩子函数的的实际应用beforecreate :举个栗子:可以在这加个loading事件created :在这结束loading ,还做一些初始化,实现函数自执行mounted : 在这发起后端请求,拿回数据,配合路由钩子做一些事情beforeDestroy : 你确认删除XX吗?destroyed :当前组件已被删除,清空相关内容3 cookie、localstrog
6、e、localSeesion的区别共同点:都是保存在浏览器端,且同源的。区别:安全性、大小、有效期、作用域1 cookie 数据始终在同源的http 请求中携带(即使不需要),即cookie 在浏览器和服务器间来回传递。而sessionStorage 和 localStorage 不会自动把数据发给服务器,仅在本地保存。cookie 数据还有路径( path )的概念,可以限制cookie 只属于某个路径下。2 存储大小限制也不同,cookie 数据不能超过4k,同时因为每次http 请求都会携带cookie ,所以 cookie 只适合保存很小的数据,如会话标识。sessionStorage
7、 和 localStorage 虽然也有存储大小的限制,但比cookie 大得多,可以达到5M 或更大。3 数据有效期不同,sessionStorage:仅在当前浏览器窗口关闭前有效,自然也就不可能持久保持; localStorage:始终有效,窗口或浏览器关闭也一直保存,因此用作持久数据;cookie 只在设置的 cookie 过期时间之前一直有效,即使窗口或浏览器关闭。4 作用域不同, sessionStorage 不在不同的浏览器窗口中共享,即使是同一个页面; localStorage 在所有同源窗口中都是共享的;cookie 也是在所有同源窗口中都是共享的。4 get 和 post 区
8、别get 参数通过url 传递, post 放在 request body 中。传递路径get 请求在 url 中传递的参数是有长度限制的,而post 没有。长度限制get 比 post 更不安全,因为参数直接暴露在url 中,所以不能用来传递敏感信息。get 请求只能进行url 编码,而post 支持多种编码方式编码方式get 请求会浏览器主动cache,而 post 支持多种编码方式。get 请求参数会被完整保留在浏览历史记录里,而post 中的参数不会被保留。GET和 POST本质上都是TCP链接 ,并无差别。但是由于HTTP的规定和浏览器安全保存/ 服务器的限制,导致他们在应用过程中体
9、现出一些不同。5 你是如何操持登录1 利用 Token 实现APP 登录成功后,服务器以某种方式,如随机生成N 位的字符串作为期,存储到服务器中,并返回Token 给 APP。后续 APP发送请求时, 都要带上该Token,每次服务器端收到请求时,Token,同时设置一个有效都要验证Token 和有效期,Token 数值对且在有效期内,服务器返回所需要的结果,否则返回错误信息,提示用户重新登录。(这种方式目前使用的最多)2 利用 Cookie 实现APP 登录成功后,服务器创建一个包含器中,并发送给APP。session_id 和Expires 两个属性值的Cookie,存储 在 服 务后续
10、APP 发送请求时,都要带上一个包含此 session_id 的 Cookie,每次服务器端收到请求时,都要验证 session_id 和有效期, session_id 数值对且在有效期内,服务器返回所需要的结果,否则返回错误信息,提示用户重新登录。6 vue 怎么实现双向数据绑定vue 数据双向绑定是通过数据劫持结合发布者 -订阅者模式的方式来实现的。 其实主要是用了 Es5 中的 Object.defineProperty ; 来劫持每个属性的 getter, 和 setter 。这也正是 Vue 不兼容 IE8 以下的原因。发布者 - 订阅者模式:订阅是请求在某些事件(event)到达时
11、可以通知它并执行对应的动作(action),而发布则相对的是向订阅告知事件(event)已经到达,你可以执行对应的动作(action)了。7 promise 的简述Promise 是异步编程 的一种解决方案,通俗的来讲Promise 是一个许诺、承诺,是对未来事情的承诺,承诺不一定能完成,但是无论是否能完成都会有一个结果。应用场景1 解决回调地狱比如我们经常可能需要异步请求一个数据之后作为下一个异步操作的入参2 promise 可以实现在多个请求发送完成后再得到或者处理某个结果最简单的实现基于上面的应用场景发现promise 可以有三种状态,分别是pending 、 Fulfilled、Rej
12、ected。Pending Promise 对象实例创建时候的初始状态Fulfilled 可以理解为成功的状态Rejected 可以理解为失败的状态构造一个 Promise 实例需要给 Promise 构造函数传入一个函数。 传入的函数需要有两个形参,两个形参都是 function 类型的参数。分别是 resolve 和 reject 。Promise 上还有 then 方法, then方法就是用来指定Promise 对象的状态改变时确定执行的操作, resolve 时执行第一个函数(onFulfilled ), reject 时执行第二个函数(当状态变为resolve 时便不能再变为reje
13、ct,反之同理。onRejected)基本api(1) new Promise(2) PromiseObj.then(resolveFn,rejectFn)resolveFn:就是Promise 对象成功的回调处理函数,指向resolverejectFn :就是Promise 对象失败的回调处理函数(3)Promise.all() 这个静态方法的参数是一个可迭代的对象,这个对象的item对象,若不是的话,就会先调用上面的Promise.resolve(item) 方法转换成新的应该都是promisepromise 对象。Promise.all() 方法返回的也是一个promise 对象。(4)
14、PromiseObj.resolve() 将一个值,数字,字符串.转换为 Promise 对象(5) Promise.reject(reason) 方法返回一个用 reason 拒绝的 Promise。你可以这样理解,返回的这个 promise 对象在初始化的时候,什么都没有做,直接给reject( your reject reson )8 es6 的了解es6 是一个新的标准,它包含了许多新的语言特性和库,是JS实质性的一次升级。新增模板字符串 (为 JavaScript提供了简单的字符串插值功能)箭头函数(操作符左边为输入的参数,而右边则是进行的操作以及返回的值Inputs=outputs
15、。)for-of (用来遍历数据例如数组中的值。)for (let index of a, b.keys() console.log(index);arguments 对象可被不定参数和默认参数完美代替。ES6将 promise 对象纳入规范,提供了原生的Promise 对象。增加了 let 和 const 命令,用来声明变量。增加了块级作用域。let命令实际上就增加了块级作用域。 ES6 规定, var命令和function命令声明的全局变量,属于全局对象的属性;let命令、const命令class 命令声明的全局变量,不属于全局对象的属性。还有就是引入module 模块的概念9 路由拦截主
16、要是利用vue-router提供的钩子函数beforeEach()对路由进行判断。* to: Route:即将要进入的目标路由对象 $route ( 常用 )* from: Route: 当前导航正要离开的路由* next: Function: 一定要调用该方法来resolve 这个钩子。执行效果依赖next 方法的调用参数。* next(): 进行管道中的下一个钩子。如果全部钩子执行完了,则导航的状态就是confirmed (确认的)。* next(false):中断当前的导航。 如果浏览器的 URL 改变了(可能是用户手动或者浏览器后退按钮),那么 URL 地址会重置到 from路由对应的
17、地址。* next( 或/者 ) next( path: 跳/转到):一个不同的地址。当前的导航被中断,然后进行一个新的导航。10 vue 路由传值(主要使用三种方法) $router.push/ name+params/ path+query方案一getDescribe(id) / 直接调用 $router.push 实现携带参数的跳转 this.$router.push(path: /describe/$id,)/ 方案一,需要对应路由配置如下: path: /describe/:id,name: Describe,component: Describe/很显然,需要在path 中添加 /
18、:id 来对应$router.push中 path 携带的参数。/ 在子组件中可以使用 $route.params.id 来获取传递的参数值。方案二/父组件中:通过路由属性中的name 来确定匹配的路由,通过params 来传递参数。this.$router.push(name: Describe,params: id: id)/对应路由配置 : 注意这里不能使用:/id 来传递参数了,因为父组件中,已经使用params 来携带参数了。path: /describe,name: Describe,component: Describe/ 子组件中:这样来获取参数$route.params.id
19、方案三/父组件:使用path会显示在url 后面 ?id=?来匹配路由,然后通过query来传递参数这种情况下query传递的参数this.$router.push(path: /describe,query: id: id)/对应路由配置:path: /describe,name: Describe,component: Describe/ 对应子组件 : 这样来获取参数 $route.query.id/ 这里要特别注意 在子组件中 获取参数的时候是 $route.params 而不是 $router11 从输入 URL到页面加载的过程1 DNS解析2 TCP连接3 发送 HTTP请求4 服
20、务器处理请求并返回 HTTP 报文5 浏览器解析渲染页面6 连接结束12 js 冒泡排序(双重 for 循环 +if 判断 +交换位置)13 http 状态码一些常见的状态码为:200 - 服务器成功返回网页404 - 请求的网页不存在503 - 服务不可用详细分解:1xx(临时响应)表示临时响应并需要请求者继续执行操作的状态代码。100 (继续) 请求者应当继续提出请求。服务器返回此代码表示已收到请求的第一部分,正在等待其余部分。101 (切换协议)请求者已要求服务器切换协议,服务器已确认并准备切换。2xx (成功) 表示成功处理了请求的状态代码。200 (成功)服务器已成功处理了请求。通常
21、,这表示服务器提供了请求的网页。201 (已创建 ) 请求成功并且服务器创建了新的资源。202 (已接受)服务器已接受请求,但尚未处理。203 (非授权信息)服务器已成功处理了请求,但返回的信息可能来自另一来源。GET 请求。204 (无内容)服务器成功处理了请求,但没有返回任何内容。205 (重置内容)服务器成功处理了请求,但没有返回任何内容。206 (部分内容)服务器成功处理了部分3xx(重定向)表示要完成请求,需要进一步操作。通常,这些状态代码用来重定向。300 (多种选择)针对请求,服务器可执行多种操作。服务器可根据请求者(user agent)选择一项操作,或提供操作列表供请求者选择
22、。301 (永久移动)请求的网页已永久移动到新位置。服务器返回此响应(对GET 或HEAD请求的响应)时,会自动将请求者转到新位置。302 (临时移动) 服务器目前从不同位置的网页响应请求,但请求者应继续使用原有位置来进行以后的请求。303 (查看其他位置)请求者应当对不同的位置使用单独的GET 请求来检索响应时,服务器返回此代码。304 (未修改)自从上次请求后,请求的网页未修改过。服务器返回此响应时,不会返回网页内容。305 (使用代理)请求者只能使用代理访问请求的网页。如果服务器返回此响应,还表示请求者应使用代理。307 (临时重定向) 服务器目前从不同位置的网页响应请求,但请求者应继续
23、使用原有位置来进行以后的请求。4xx(请求错误)这些状态代码表示请求可能出错,妨碍了服务器的处理。400 (错误请求)服务器不理解请求的语法。401 (未授权)请求要求身份验证。对于需要登录的网页,服务器可能返回此响应。403 (禁止)服务器拒绝请求。404 (未找到)服务器找不到请求的网页。405 (方法禁用)禁用请求中指定的方法。406 (不接受)无法使用请求的内容特性响应请求的网页。407 (需要代理授权)此状态代码与401(未授权)类似,但指定请求者应当授权使用代理。408 (请求超时)服务器等候请求时发生超时。409 (冲突)服务器在完成请求时发生冲突。服务器必须在响应中包含有关冲突
24、的信息。410 (已删除)如果请求的资源已永久删除,服务器就会返回此响应。411 (需要有效长度)服务器不接受不含有效内容长度标头字段的请求。412 (未满足前提条件)服务器未满足请求者在请求中设置的其中一个前提条件。413 (请求实体过大)服务器无法处理请求,因为请求实体过大,超出服务器的处理能力。414 (请求的URI 过长)请求的URI(通常为网址)过长,服务器无法处理。415 (不支持的媒体类型)请求的格式不受请求页面的支持。416 (请求范围不符合要求)如果页面无法提供请求的范围,则服务器会返回此状态代码。417 (未满足期望值)服务器未满足期望 请求标头字段的要求.5xx(服务器错
25、误)这些状态代码表示服务器在尝试处理请求时发生内部错误。而不是请求出错。这些错误可能是服务器本身的错误,500(服务器内部错误)服务器遇到错误,无法完成请求。501(尚未实施)服务器不具备完成请求的功能。例如,服务器无法识别请求方法时可能会返回此代码。502(错误网关)服务器作为网关或代理,从上游服务器收到无效响应。503(服务不可用)服务器目前无法使用(由于超载或停机维护)。通常,这只是暂时状态。504(网关超时)服务器作为网关或代理,但是没有及时从上游服务器收到请求。505( HTTP 版本不受支持) 服务器不支持请求中所用的HTTP 协议版本。HttpWatch 状态码 Result i
26、s200 - 服务器成功返回网页,客户端请求已成功。302 - 对象临时移动。服务器目前从不同位置的网页响应请求,但请求者应继续使用原有位置来进行以后的请求。304 - 属于重定向。自上次请求后,请求的网页未修改过。服务器返回此响应时,不会返回网页内容。401 - 未授权。请求要求身份验证。对于需要登录的网页,服务器可能返回此响应。404 - 未找到。服务器找不到请求的网页。2xx - 成功。表示服务器成功地接受了客户端请求。3xx - 重定向。表示要完成请求,需要进一步操作。客户端浏览器必须采取更多操作来实现请求。例如,浏览器可能不得不请求服务器上的不同的页面,或通过代理服务器重复该请求。4
27、xx - 请求错误。这些状态代码表示请求可能出错,妨碍了服务器的处理。5xx - 服务器错误。表示服务器在尝试处理请求时发生内部错误。 这些错误可能是服务器本身的错误,而不是请求出错。14 js 中的原型链每个对象都会在其内部初始化一个属性,就是prototype( 原型 ),当我们访问一个对象的属性时,如果这个对象内部不存在这个属性,那么他就会去prototype 里找这个属性,这个prototype又会有自己的prototype ,于是就这样一直找下去,也就是我们平时所说的原型链的概念。应用:原型链是实现继承的主要方法。15 闭包是什么,有什么特性,对页面有什么影响通俗的讲:就是函数a 的
28、内部函数b,被函数 a 外部的一个变量引用的时候,就创建了一个闭包。闭包的特性:.封闭性:外界无法访问闭包内部的数据,如果在闭包内声明变量,外界是无法访问的,除非闭包主动向外界提供访问接口;.持久性:一般的函数,调用完毕之后,系统自动注销函数,而对于闭包来说,在外部函数被调用之后,闭包结构依然保存在系统中,闭包中的数据依然存在,从而实现对数据的持久使用。优点: 减少全局变量。 减少传递函数的参数量 封装;缺点:使用闭包会占有内存资源,过多的使用闭包会导致内存溢出等.16 怎么实现跨域请求1、 jsonp最常见的一种跨域方式, 其背后原理就是利用了 script 标签不受同源策略的限制, 在页面
29、中动态插入了 script ,script 标签的 src 属性就是后端 api 接口的地址, 并且以 get 的方式将前端回调处理函数名称告诉后端,后端在响应请求时会将回调返还,并且将数据以参数的形式传递回去。 jsonp 只能发送 get 请求。2、 CORSCross-Origin Resource Sharing(跨域资源共享)是一种允许当前域(origin )的资源(比如html/js/web service )被其他域(origin )的脚本请求访问的机制。当使用XMLHttpRequest 发送请求时,浏览器如果发现违反了同源策略就会自动加上一个请求头origin,后端在接受到请
30、求后确定响应后会在Response Headers中加入一个属性Access-Control-Allow-Origin ,值就是发起请求的源地址(http:/127.0.0.1:8888) ,浏览器得到响应会进行判断Access-Control-Allow-Origin的值是否和当前的地址相同,只有匹配成功后才进行响应处理。现代浏览器中和移动端都支持CORS(除了opera mini ), IE下需要8+3、服务器跨域在前后端分离的项目中可以借助服务器实现跨域, 具体做法是: 前端向本地服务器发送请求,本地服务器代替前端再向真实服务器接口发送请求进行服务器间通信,本地服务器其实充当个中转站的角
31、色,再将响应的数据返回给前端缺点:服务器跨域需要另起服务器4、 postmessage跨域在HTML5中新增了postMessage方法, postMessage可以实现跨文档消息传输CrossDocument Messaging ,IE8, Firefox 3, Opera 9, Chrome 3和Safari 4都支持postMessage 。该方法可以通过绑定window的 message 事件来监听发送跨文档消息传输内容。使用postMessage 实现跨域的话原理就类似于jsonp,动态插入iframe 标签,再从拿回数据,私认为用作跨页面通信更加适合iframe里面总结当然还有其他
32、实现跨域的方式比如在 ie8、9 下域方案,都各有利弊,比如: jsonp 只能发送XDR 跨域方案, flash 方案, 以上是一些常用的跨get 请求、服务器跨域需要另起服务器等等,大家可以根据自己项目需求选择适合的解决方案,17 介绍一下 js 的同源策略 -安全同源策略是由Netscape 提出的著名安全策略,是浏览器最核心、基本的安全功能,它限制了一个源( origin )中加载文本或者脚本与来自其他源(origin )中资源的交互方式,所谓的同源就是指协议、域名、端口相同。当浏览器执行一个脚本时会检查是否同源,只有同源的脚本才会执行,如果不同源即为跨域18 引入样式表的方式内样式、
33、内部样式表、外部样式表。一 行内样式使用 style 属性引入CSS样式。二 内部样式表在 style 标签中书写 CSS代码。 style 标签写在 head 标签中。三 外部样式表CSS代码保存在扩展名为.css 的样式表中HTML 文件引用扩展名为.css 的样式表,有两种方式:链接式、导入式。19 面向对象、面向过程的区别面向过程就是分析出解决问题所需要的步骤,然后用函数把这些步骤一步一步实现,使用的时候一个一个依次调用就可以了。面向对象是把构成问题事务分解成各个对象,建立对象的目的不是为了完成一个步骤,而是为了描叙某个事物在整个解决问题的步骤中的行为。面向过程优点:性能比面向对象高,
34、因为类调用时需要实例化,开销比较大,比较消耗资源机、嵌入式开发、 Linux/Unix 等一般采用面向过程开发,性能是最重要的因素。;比如单片缺点:没有面向对象易维护、易复用、易扩展。面向对象优点:易维护、易复用、易扩展,由于面向对象有封装、继承、多态性的特性,可以设计出低耦合的系统,使系统 更加灵活、更加易于维护缺点:性能比面向过程低20 面向对象的特点1.封装所谓封装,就是将客观事物封装成抽象的类,并且类可以把数据和方法让可信的类或者对象进行操作, 对不可信的类或者对象进行隐藏。类就是封装数据和操作这些数据代码的逻辑实体。在一个类的内部,某些属性和方法是私有的,不能被外界所访问。通过这种方
35、式,对象对内部数据进行了不同级别的访问控制,就避免了程序中的无关部分的意外改变或错误改变了对象的私有部分。2.继承继承有这样一种能力,就是能使用现有的类的所有功能,并无须重新编写原来的这些类的基础上对这些功能进行扩展。通过继承创建的新类称为子类或派生类,被继承的称为基类。继承有两种,一种是实现继承,另外一种是接口继承。实现继承可以直接使用基类的属性和方法而无需额外编码,接口继承是指使用属性和方法的名称,但是子必须提供实现的能力。3.多态所谓多态就是对一个实例的相同方法在不同的情形下有不同的表现形式。多态机制使得不同内部结构的对象可以共享相同的外部接口,这就意味着,虽然不同的类的内部操作不同,但
36、可以通过一个公共的类,它们可以通过相同的方式予以调用。21 jquery 动画jQuery animate()方法用于创建自定义动画。语法: $(selector).animate(params,speed,callback);必需的params参数定义形成动画的CSS 属性。可选的speed参数规定效果的时长。它可以取以下值:slow 、 fast或毫秒。可选的callback参数是动画完成后所执行的函数名称。22 数组去重1.遍历数组法它是最简单的数组去重方法(indexOf方法)实现思路:新建一个数组,遍历去要重的数组,当值不在新数组的时候(indexOf为 -1)就加入该新数组中;va
37、r arr=2,8,5,0,5,2,6,7,2;function unique1(arr)var hash=;for (var i = 0; i arr.length; i+) if( hash.indexOf(arri)=-1)hash.push(arri);return hash;2.数组下标判断法调用indexOf方法,性能和方法1 差不多实现思路: 如果当前数组的第i 项在当前数组中第一次出现的位置不是i,那么表示第i 项是重复的,忽略掉。否则存入结果数组。function unique2(arr)var hash=;for (var i = 0; i arr.length; i+) if(arr.indexOf(arri)=i)hash.push(arri);return hash;3.排序后相邻去除法实现思路:给传入的数组排序,排序后相同的值会相邻,然后遍历排序后数组时,新数组只加入不与前一值重复的值。function unique3(arr)arr.sort();var hash=arr0;for (var i = 1; i arr.length; i+) if(arri!=hashhash.length-1)hash.push(arri);return hash;4.优化遍历数组法(推荐)实现思路:双层循环,外循环表示从0 到 arr.length ,内