毕业后一直在合肥的一家小公司工作。没有老司机,没有技术氛围。只能在技术的道路上独自摸索。老板只能画饼充饥,前途迷茫,看不到希望。于是乎,我毅然辞职,在新年伊始来到了杭州。这里的互联网公司数量应该是合肥的几十倍。...刚来3天,面试了好几家公司,有的比较小,有的是创业公司,有的发展不错;今天总结一下最近的面试题,给自己做个复习。栈主要是Vue,所以大部分话题都是和Vue开发相关的。1.谈谈你对MVVM开发模型的理解。MVVM分为三部分:Model、View、ViewModel。Model代表数据模型,数据和业务逻辑定义在Model层;View代表UI视图,负责数据的展示;ViewModel负责监控Model中的数据变化并控制视图的更新,处理用户交互操作;Model和View没有直接关联,但是通过ViewModel,Model和ViewModel之间存在双向的数据绑定关系。因此,当Model中的数据发生变化时,会触发View层的刷新,View中因用户交互而发生变化的数据也会同步到Model中。这种模式实现了Model和View之间数据的自动同步,开发者只需要专注于数据的维护和操作,而不需要自己去操作dom。2、Vue有哪些命令?v-html、v-show、v-if、v-for等。3.v-if和v-show有什么区别?v-show只控制元素的显示方式,在block和none之间切换display属性;而v-if控制着这个DOM节点的存在与否。当我们需要频繁切换某个元素的显示/隐藏时,使用v-show会节省更多的性能开销;当我们只需要显示或隐藏一次时,使用v-if更合理。4.简述Vue的响应式原理当一个Vue实例被创建时,Vue会遍历data选项的属性,使用Object.defineProperty将它们转化为getters/setters并在内部跟踪相关的依赖关系,当属性被访问和访问时通知改良品种。每个组件实例都有一个对应的watcher程序实例,在组件渲染过程中会将该属性记录为一个依赖,然后当依赖的setter被调用时,会通知watcher重新计算,从而导致其关联的组件被更新。5、如何在Vue中实现组件内部的双向数据绑定?假设有一个输入框组件。当用户进入时,同步父组件页面中的数据。具体思路:父组件通过props传值给子组件,子组件通过$emit通知父组件修改对应的props值。具体实现如下:importVuefrom'vue'constcomponent={props:['value'],template:`
`,data(){return{}},methods:{handleInput(e){this.$emit('input',e.target.value)}}}newVue({components:{CompOne:component},el:'#root',模板:`
`,data(){return{value:'123'}}})可以看出,当输入数据时,父子组件中的数据是同步变化的:我们在父组件中做了两件事,一是传递props给子组件,另一个是监听输入事件并同步他们自己的值属性。那么这两步可以简化吗?答案是可以的,只需要修改父组件:template:`
`v-model其实会帮我们完成以上两步。6、Vue中如何监听一个属性值的变化?比如现在需要监控data中obj.a的变化。在Vue中可以这样监控对象属性的变化:watch:{obj:{handler(newValue,oldValue){console.log('objchanged')},deep:true}}deepproperty表示深度遍历,但是这样写这样会监听obj的所有属性的变化,并不是我们想要的效果,所以做一些修改:watch:{'obj.a':{handler(newName,oldName){console.log('obj.changed')}}}还有一个方法可以通过computed来实现,就是:computed:{a1(){returnthis.obj.a}}是利用computed属性的特性来实现的。当依赖关系发生变化时,将重新计算一个新值。7、Vue中data中的object属性添加新属性会出现什么情况,如何解决?示例:
点击按钮,会发现obj.b已经添加成功,但是view还没有被刷新:原因是在创建Vue实例的时候,没有声明obj.b,所以没有被Vue转化为响应式属性,自然不会触发视图的更新。这时候就需要用到Vue的全局api$set():addObjB(){//this.obj.b='obj.b'this.$set(this.obj,'b','obj.b')console.log(this.obj)}$set()方法相当于手动将obj.b处理成响应式属性,此时view也会发生变化:8.delete和Vue.deletedelete的区别arraydelete只是被删除的元素变为空/undefined而其他元素的键值保持不变。vue.delete直接删除数组,改变数组的键值。vara=[1,2,3,4]varb=[1,2,3,4]deletea[1]console.log(a)this.$delete(b,1)console.log(b)9。如何优化SPA应用首屏加载速度慢?通过script标签导入公共JS库,减小app.bundel体积,让浏览器并行下载资源文件,提高下载速度;配置路由时,采用懒加载方式引入页面和组件,进一步缩小应用体积。bundle的大小,然后在调用某个组件时加载相应的js文件;添加首屏加载图像以改善用户体验;10、如何优化网站前端的性能?1、减少HTTP请求次数浏览器与服务器通信时,主要通过HTTP进行通信。浏览器和服务器需要经过三次握手,每次握手都需要很多时间。而且,不同浏览器对资源文件的并发请求数是有限制的(不同浏览器允许并发数)。一旦HTTP请求达到一定数量,就会出现资源请求的等待状态,这是致命的。因此,减少HTTP请求的数量可以在一定程度上优化网站性能。CSSSprites:国内俗称CSSsprites,这是一种通过将多张图片合并为一张图片来减少HTTP请求的解决方案,可以通过CSS背景属性访问图片的内容。该解决方案还可以减少图像的总字节数。合并CSS和JS文件:前端有很多工程打包工具,例如:grunt、gulp、webpack等,为了减少http请求的次数,可以使用这些工具来合并多个css或者多个js发布前将文件合并为一个文件。使用lazyLoad:俗称延迟加载,它可以控制网页上的内容一开始不加载,不发送请求,当用户操作真正需要的时候才加载内容。这样就控制了对web资源的一次性请求次数。1、控制资源文件加载优先级浏览器在加载HTML内容时,会从上到下依次解析HTML内容,解析到一个链接或script标签时,会加载href或src对应的链接内容,从而为了在第一时间展示页面给用户,需要提前加载CSS,以免被JS加载影响。一般来说,CSS在最前面,JS在最下面。1、使用浏览器缓存浏览器缓存是将网络资源存储在本地,等待下一次对该资源的请求。如果资源已经存在,则不需要再去服务器重新请求资源,直接在本地读取资源。2.减少回流(Reflow)基本原理:回流是影响元素几何属性(宽度和高度)的DOM变化。浏览器会重新计算元素的几何属性,这会使渲染树受影响的部分失效。浏览器会验证DOM树中所有其他节点的可见性属性,这就是Reflow效率低下的原因。如果Reflow过于频繁,CPU使用率会急剧上升。减少回流。如果在DOM操作过程中需要添加样式,尽量使用增加class属性,而不是通过style来操作样式。减少DOM操作图标替换为IconFont11.网页从输入URL到渲染要经过什么过程?大致可以分为以下7个步骤:输入网址;发送到DNS服务器,获取域名对应的web服务器对应的ip地址;与网络服务器建立TCP连接;浏览器向web服务器发送http请求;Web服务器响应请求,并返回指定url的数据(或错误信息,或重定向的新url地址);浏览器下载web服务器返回的数据并解析html源文件;生成DOM树,解析css和js,渲染页面,直到显示完成;12、jQuery获取的dom对象和原生的dom对象有什么区别?js原生获取的dom是一个对象,而jQuery对象是一个数组对象,实际上是被选中元素的数组集合,所以它们是不同的对象类型,并不等价。将原生DOM对象转换为jQuery对象:varbox=document.getElementById('box');var$box=$(box);将jQuery对象转换为原生DOM对象:var$box=$('#box');varbox=$box[0];13。jQuery如何扩展自定义方法(jQuery.fn.myMethod=function(){alert('myMethod');})//或:(function($){$.fn.extend({myMethod:function(){alert('myMethod');}})})(jQuery)使用:$("#div").myMethod();目前公司的面试题都是比较基础的,但是对于一些不去研究它的原理,只追求会用的同学,可能就没那么容易了。因此,我们不仅要追求学习的广度,更要追求深度。OK,希望能尽快拿到心仪的offer。