问题
1. 为什么 v-for 和 v-if 哪个优先级更高?为什么不建议用在一起?
vue2
版本中v-for
优先级高于v-if
,这意味着v-if
将分别重复运行于每个v-for
循环中。如果要遍历的数组很大,而真正要展示的数据很少时,这将造成很大的性能浪费vue3
版本中v-if
优先级高于v-for
,所以在v-if
执行时,判断的变量还不存在,会导致异常
解决方案:
- 使用计算属性,将符合条件的列表过滤出来,例如
users.filter(u => u.isActive)
- 在上一层元素进行判断(判断整个列表是否展示的场景)
2. 子组件是否可以直接修改父组件数据?
可以修改,但违背 vue
单项数据流原则,浏览器也会发出警告,应该使用 $emit
通知父组件进行修改
3. 说说你对 vue 响应式的理解
4. 什么是运行时和编译时?
对于 runtime-with-compiler
版本的挂载过程是,根据 template、el
获取 render
函数,创建 Render Watcher
,在创建Render Watcher
的过程中触发挂载过程;即调用 render
函数获取渲染 VNode
,调用 patch
函数创建节点并渲染到页面上。其过程是在 beforeMount
与 mounted
之间。
对于 runtime
版本,由于在打包构建的时候已经将模版转成了 render
函数,所以省略了获取 render
的步骤;会直接创建 Render Watcher
,在创建 Render Watcher
的过程中触发挂载过程;即调用 render
函数获取渲染VNode
,调用 patch
函数创建节点并渲染到页面上。
5. Vue.extend 原理?
Vue.extend
的作用就是构造一个 Vue
的子类,它使用原型继承的方式创建了一个继承于 Vue
的构造器 Sub
,并返回。然后对 Sub
这个对象本身扩展了一些属性,如扩展 options
、添加全局 API
等;并且对配置中的 props
和 computed
做了初始化工作;将其代理到构造函数的原型上,目的是,每次实例化组件实例时不需要再次代理,从而减少代码执行次数。最后对 Sub
构造函数做了缓存,避免多次继承同一个构造函数。
6. npm run xxx 发生了什么?
以 vue-cli
的 npm run serve
为例:
- 运行
npm run serve
的时候,npm
会先在项目的package.json
文件中找到scripts
中对应的serve
命令,根据serve
对应的vue-cli-service serve
,去当前目录的node_modules/.bin
查找要执行的程序,如果找到则运行; - 没有找到则从全局的
node_modules/.bin
中查找,npm i -g xxx
就是安装到全局目录; - 如果全局目录还是没找到,那么就从
path
环境变量中查找有没有其它同名的可执行程序; - 如果都没有就报异常
7. .sync
与 v-model
区别
两者行为一致,.sync
支持多个值,其更新方式为 @update:value="xxx = $event"