1. 讲一讲mvvm框架
mvvm是 model-view-viewmodel的缩写.也就是把mvc中的Controller演变成了viewmodel.
Model层代表数据模型, View层代表ui组件, viewModel是view和model层的桥梁, 数据绑定到viewmodel层并自动将数据渲染到view上,视图改变时候会通知viewmodel层更新数据
2. 介绍下vue响应式系统
vue会对使用Object.defineProperty对data的getter/setter方法进行拦截, 结合发布订阅模式,在getter中进行订阅,在setter中进行发布通知,让所有订阅者完成响应
3. 那你知道vue3.0响应式数据原理么
vue3 改用proxy替代Object.defineProperty.因为proxy可以直接监听对象和数组的变化.
4. computed与watch的区别
计算属性computed和监听器watch都可以观察属性的变化而做出响应
不同点: Computed
本质是一个具备缓存的watcher,依赖的属性发生变化就会更新视图。 适用于计算比较消耗性能的计算场景。当表达式过于复杂时,在模板中放入过多逻辑会让模板难以维护,可以将复杂的逻辑放入计算属性中处理。Watch
没有缓存性,更多的是观察的作用,可以监听某些数据执行回调。当我们需要深度监听对象中的属性时,可以打开deep:true
选项,这样便会对对象中的每一项进行监听。这样会带来性能问题,优化的话可以使用字符串形式
监听,如果没有写到组件中,不要忘记使用unWatch手动注销
哦
5. 介绍下vue的生命周期
beforeCreate
是new Vue()之后触发的一个钩子, 在当前阶段data, methods computed 以及watch上的数据和方法都不能访问created
在实例创建完成后发生. 当前阶段已经完成了数据观你测,也就是可以使用数据,更改数据, 在这里更改数据不会触发updated函数, 可以做一些初始数据获取, 在当前阶段无法和dom进行交互beforeMount
发生在挂载之前,在这之前template模板已导入渲染函数编译, 而当前阶段虚拟dom已经创建完成, 即将开始渲染,在此时也可以对数据进行修改mounted
在挂载完成后发生,在当前阶段,真实的dom挂载完成, 数据完成双向绑定,可以访问到dom节点beforeUpdate
发生在更新之前,也就是响应式数据发生更新, 虚拟dom重新渲染前被触发updated
发生在更新完成之后,当前阶段组件dom已完成更新beforeDestory
发生在实例销毁之前,在当前阶段实例完全可以被使用, 我们可以在这里做善后收尾工作, 比如清除定时器destroyed
发生在数据实例销毁之后,这个时候只剩下dom空壳, 组件已被拆解,数据绑定解除, 监听移除,
6. 组件之间怎么通信
父子组件通信
父组件 > 子组件 prop
子组件 > 父组件 $emit
获取组件实例
使用$parent/$childred
$refs.xxx
兄弟组件通信
event bus
vuex
跨组件通信
provide/inject
event bus
vuex
7. Vue事件绑定原理说一下
组件事件绑定: 每一个vue实例都是一个event bus, 当子组件被创建的时候,父组件将事件传递给子组件, 子组件初始化的时候是有$on方法将事件注册到内部, 需要的时候使用$emit触发函数
而对于原生native事件,使用addEventListener绑定到真实的dom上
8. vue模板渲染的原理是什么
vue中的模板template无法被浏览器解析并渲染,因为这不属于浏览器的标准, 不是正确的html语法, 所以需要将template转化为一个javascript函数, 这样浏览器就可以执行这一个函数并渲染出对应的html元素,就可以让视图跑起来了.这个转化过程,就成为模板编译
模板编译又分为三个阶段,解析parse 优化optimize 生成generate,最终生成可执行函数render
parse阶段: 使用大量的正则表达式对template字符串进行解析,将标签 指令 属性等转化为抽象语法树AST
optimise阶段: 遍历AST,找到其中的一些静态节点并进行标记,方便在页面重渲染的时候进行diff比较时,直接跳过这一些静态节点.
generate阶段: 将最终的AST转化为render函数字符串
9. template预编译是什么
对于vue组件来说,模板编译只会在组件实例化的时候编译一次,生成渲染函数后再也不会进行编译,
而模板编译的目的也不仅仅是将template转化为render function
这个过程,正好可以在项目构建的过程中完成,这样可以让实际组件在runtime时直接跳过模板渲染,进而提升性能,这个在项目构建的编译template的过程,就是预编译
10. template和jsx有什么区别
对于runtime来说,只需要保证组件存在render函数即可,而我们有了预编译之后,我们只需要保证构建过程中生成render函数就可以
在webpack中,我们是要vue-loader编译.vue文件, 内部依赖的vue-template-compiler模块, 在webpack构建过程中,将template预编译成render函数
JSX相对于template而言,具有更高的灵活性,在复杂的组件中,更具有优势,而 template 虽然显得有些呆滞。但是 template 在代码结构上更符合视图与逻辑分离的习惯,更简单、更直观、更好维护。
11. 说下什么是virtual dom
virtual dom是dom节在javascript中的一种抽象数据结构,之所以需要虚拟dom.是因为浏览器中操作dom的代价比较昂贵,频繁的操作dom会产生性能问题,虚拟dom的作用是在每一次响应式数据发生变化引起页面重渲染时,vue对比更新前后的虚拟dom,匹配找出尽可能少的需要更新的真实dom,从而提高性能的目的
12 介绍下vue中的diff算法
13 key属性的作用
在对节点进行diff的过程中,判断是否为相同节点的一个很重要的条件是key是否相等, 如果是相同节点, 则会尽可能的复用原有的dom节点,
14. 说说vue2.0和3.0的区别
- 重构响应式系统 使用proxy替换object.defineProperty,使用proxy优势:
- 可直接监听数组类型的数据变化
- 监听的目标为对象,不需要像object.defineProperty一样遍历每个属性,有一定的性能提升
- 可拦截apply ownKeys has等13种方法,
- 直接实现对象属性的新增/删除
- 新增composition Api 更好的逻辑复用和代码组织
- 重构virtual Dom
- 模板编译是的优化,将一些静态节点编译成常量
- slot优化,将slot编译为lazy函数, 将slot的渲染的决定权交给子组件
- 代码结构调整,体积更小
- 使用typescript 替换flow
15. 为什么要新增composition Api
在vue2.0中,随着功能的增加,组件变得越来越复杂,越来越难维护, 而难以维护的根本原因是vue的api设计迫使开发者使用watch computed methods选项组织代码,而不是实际业务逻辑
另外vue2 缺少一种较为简洁的低成本的机制来完成逻辑复用,虽然可以minxis完成逻辑复用,但是当mixin变多的时候,会使得难以找到对应的data computed或者method来源于那个mixin,
所以CompositionAPI的出现,主要也是解决option API带来的问题,
第一个就是代码组织的问题,composition API可以让开发者根据业务逻辑组织自己的代码, 让代码具备更好的可读性和可扩展性
第二个就是实现代码的逻辑提取和复用,
16. 都说compositionApi与react hook很像,说说区别
composition API 是基于vue的响应式系统实现的,
声明在setup函数内, 一次组件实例化只调用一次setup, 而React Hook每次重渲染都需要调用hook, 使得react性能相对于vue比较慢
compostion API的调用不需要顾虑调用顺序, 也可以在循环 条件 嵌套函数中使用
响应式系统自动实现了依赖收集,进而组件的部分的性能优化由vue内部自己完成,
17.SSR有了解么? 原理是什么
在客户端请求服务器的时候,服务器到数据库中获取到相关的数据,并且在服务器内部将Vue组件渲染成HTML,并且将数据、HTML一并返回给客户端,这个在服务器将数据和组件转化为HTML的过程,叫做服务端渲染SSR。
而当客户端拿到服务器渲染的HTML和数据之后,由于数据已经有了,客户端不需要再一次请求数据,而只需要将数据同步到组件或者Vuex内部即可。除了数据意外,HTML也结构已经有了,客户端在渲染组件的时候,也只需要将HTML的DOM节点映射到Virtual DOM即可,不需要重新创建DOM节点,这个将数据和HTML同步的过程,又叫做客户端激活。
使用SSR的好处:
- 有利于SEO:其实就是有利于爬虫来爬你的页面,因为部分页面爬虫是不支持执行JavaScript的,这种不支持执行JavaScript的爬虫抓取到的非SSR的页面会是一个空的HTML页面,而有了SSR以后,这些爬虫就可以获取到完整的HTML结构的数据,进而收录到搜索引擎中。
- 白屏时间更短:相对于客户端渲染,服务端渲染在浏览器请求URL之后已经得到了一个带有数据的HTML文本,浏览器只需要解析HTML,直接构建DOM树就可以。而客户端渲染,需要先得到一个空的HTML页面,这个时候页面已经进入白屏,之后还需要经过加载并执行 JavaScript、请求后端服务器获取数据、JavaScript 渲染页面几个过程才可以看到最后的页面。特别是在复杂应用中,由于需要加载 JavaScript 脚本,越是复杂的应用,需要加载的 JavaScript 脚本就越多、越大,这会导致应用的首屏加载时间非常长,进而降低了体验感。
借鉴网址
vue20道面试
https://juejin.im/post/684490...
聊聊对vue.js框架的理解
https://github.com/yacan8/blo...
尤大大总结
https://juejin.im/post/684490...