v-if和v-for的优先级
v-for的优先级高于v-if,如果同时出现,每次渲染都会先执行循坏再判断条件,所以循坏是不可避免的,就浪费性能,避免情况可以在外面套一层template,在这一层进行v-if判断,然后在内部进行v-for循坏。如果要用条件判断是否能循坏,可以用computed进行条件过滤,或者一开始就对数组map出可循坏的数据。
vue组件的data为什么必须是个函数而vue的根实例没有此限制
根实例app的通过new的形式,只有一个,单例模式,在vue源码的init.js里面,根实例会走mergeOptions。检测data合并选项的检查方法,会先检测组件,mergeDataOrFn。vue组件可能存在多个实例,如果使用对象定义data,导致公用一个data对象,状态更新会影响所有组件实例,不合理。要采用函数形式来定义,在initData会将作为工厂函数返回全新的data对象
vue中的key工作原理
从左到右对比节点是否相同,到不同的时候再从右到左,相同的节点不进行更新操作,不相同的节点都会更新 。
vue中的diff算法
lifecycle.js的mountComponent方法有个watcher对象,组件每执行mount的时候会创建一个watcher实例,组件中可能存在很多个data的key使用,界面中多个节点变化的时候,可以用diff算法进行新旧两次变化比较。在patch.js中有patchVnode方法,是diff发生变化的地方。先判断是否有子节点,同层比较
diff算法是虚拟dom技术必然产物,因为虚拟dom变化要和真实dom变化做对比,通过新旧dom对比,将真实的变化更新在真实dom上,diff高效执行对比,降低时间复杂度o(n) 。
当我修改数据的时候,数据响应式会触发setter,会通知到watcher队列,执行更新函数,对比上一次oldVnode,和新的节点newVnode,这个过程称为patch ,key就可以精准找到相同的节点,