v-show和v-if的区别
v-if:控制dom元素的显示或隐藏是将DOM元素整个添加或删除;
v-show:控制DOM的显示或隐藏是为DOM元素动态的添加css样式 display,设置成 block 或者 none DOM元素还是存在的。
为何v-for中要用key
1.vue中列表循环需加:key=“唯一标识” 唯一标识尽量是item里面id等,因为vue组件高度复用增加Key可以标识组件的唯一性,为了更好地区别各个组件 key的作用主要是为了高效的更新虚拟DOM。
2.key主要用来做dom diff算法用的,diff算法是同级比较,比较当前标签上的key还有它当前的标签名,如果key和标签名都一样时只是做了一个移动的操作,不会重新创建元素和删除元素。
3.没有key的时候默认使用的是“就地复用”策略。如果数据项的顺序被改变,Vue不是移动Dom元素来匹配数据项的改变,而是简单复用原来位置的每个元素。如果删除第一个元素,在进行比较时发现标签一样值不一样时,就会复用之前的位置,将新值直接放到该位置,以此类推,最后多出一个就会把最后一个删除掉。
4.尽量不要使用索引值index作key值,一定要用唯一标识的值,如id等。因为若用数组索引index为key,当向数组中指定位置插入一个新元素后,因为这时候会重新更新index索引,对应着后面的虚拟DOM的key值全部更新了,这个时候还是会做不必要的更新,就像没有加key一样,因此index虽然能够解决key不冲突的问题,但是并不能解决复用的情况。如果是静态数据,用索引号index做key值是没有问题的。
5.标签名一样,key一样这时候就会就地复用,如果标签名不一样,key一样不会复用。
描述Vue组件生命周期
- 什么是vue生命周期
Vue 实例从创建到销毁的过程,就是生命周期。也就是从开始创建、初始化数据、编译模板、挂载Dom→渲染、更新→渲染、卸载等一系列过程,我们称这是 Vue 的生命周期。 - vue生命周期的作用是什么
它的生命周期中有多个事件钩子,让我们在控制整个Vue实例的过程时更容易形成好的逻辑 - vue生命周期总共有几个阶段
它可以总共分为8个阶段:创建前/后, 载入前/后,更新前/后,销毁前/销毁后 - 第一次页面加载会触发哪几个钩子
第一次页面加载时会触发 beforeCreate, created, beforeMount, mounted 这几个钩子 - DOM 渲染在 哪个周期中就已经完成
DOM 渲染在 mounted 中就已经完成了。 - 简单描述每个周期具体适合哪些场?
生命周期钩子的一些使用方法: beforecreate : 可以在这加个loading事件,在加载实例时触发 created : 初始化完成时的事件写在这里,如在这结束loading事件,异步请求也适宜在这里调用 mounted : 挂载元素,获取到DOM节点 updated : 如果对数据统一处理,在这里写上相应函数 beforeDestroy : 可以做一个确认停止事件的确认框 nextTick : 更新数据后立即操作dom
Vue组件如何通讯
1、vue父组件向子组件传值的方法是什么?
在父组件中给子组件标签上绑 定一个属性, 属性上挂载需要传递的值
在子组件通过props:[“自定义属性名”]来接收数据
2、vue子组件向父组件传值的方法是什么?
(1) 在父组件中给子组件绑定一个自定义事件,给这个事件挂载需要调用的方法
(2) 在子组件的方法通过this.$emit(‘自定义事件名’)来调用这个方法
3、vue非父子组件传值的方法是什么?
(1) 创建一个空的vue实例BUS
(2) 通过BUS.$emit(‘事件名’)传到空的vue实例中
(3) 通过BUS.$on(‘事件名’,(参数)=>{挂载从子1传来的数据})来接收
描述组件渲染和更新的过程
1、vue 组件初次渲染过程
解析模板为 render 函数
触发响应式,监听 data 属性的 getter 和 setter
执行 render 函数, 生成 vnode,patch(elem,vnode)
2、vue 组件更新过程
修改 data, 触发 setter (此前在getter中已被监听)
重新执行 render 函数,生成 newVnode
patch(vnode, newVnode)
双向数据绑定v-model的实现原理
vue.js 则是采用数据劫持结合发布者-订阅者模式的方式,通过Object.defineProperty()来劫持各个属性的setter,getter,在数据变动时发布消息给订阅者。
var obj = {};
Object.defineProperty(obj, 'name', {
get: function() {
console.log('获取了')
return val;
},
set: function (newVal) {
console.log('设置了')
}
})
obj.name = 'yzg'; / /在给obj设置name属性的时候,触发了set这个方法
var val = obj.name; //在得到obj的name属性,会触发get方法
实现最简单的双向绑定
通过Object.defineProperty()可以实现数据劫持,是的属性在赋值的时候触发set方法
<!doctype html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
</head>
<body>
<div id="vue-demo"></div>
<input type="text" id="input">
<script>
var obj = {};
var Demo = document.getElementById('#vue-demo')
var Inp = document.getElementById("#input")
Object.defineProperty(obj, 'name', {
get: function() {
return val;
},
set: function (newVal) { . //当该属性被赋值的时候触发
Inp.value = newVal;
Demo.innerHTML = newVal;
}
})
input.addEventListener('input', function(e) {
// 给obj的name属性赋值,进而触发该属性的set方法
obj.name = e.target.value;
});
obj.name = 'yzg';//在给obj设置name属性的时候,触发了set这个方法
</script>
</body>
</html>