第2章 Vue.js基础语法
第4节:条件与列表渲染
在Vue.js中,条件渲染和列表渲染是常用的功能,它们允许我们根据数据动态地显示或隐藏元素,以及渲染列表数据。
2.4.1 条件渲染指令详解
Vue提供了多种条件渲染指令,用于根据表达式的值来决定是否渲染元素。
1. v-if、v-else-if、v-else
v-if指令用于条件性地渲染一块内容,只有当表达式返回真值时才会渲染。
<template>
<!-- 基本使用 -->
<h1 v-if="showTitle">欢迎使用Vue.js</h1>
<!-- v-else-if 和 v-else -->
<div class="user-type">
<p v-if="userType === 'admin'">管理员用户</p>
<p v-else-if="userType === 'editor'">编辑用户</p>
<p v-else-if="userType === 'visitor'">访客用户</p>
<p v-else>未知用户类型</p>
</div>
<!-- 嵌套使用 -->
<div v-if="hasPermission">
<p v-if="userType === 'admin'">管理员权限</p>
<p v-else>普通用户权限</p>
</div>
</template>
<script>
export default {
data() {
return {
showTitle: true,
userType: 'admin',
hasPermission: true
}
}
}
</script>2. v-show vs v-if性能对比
v-show指令也用于条件性地显示元素,但它与v-if有一些重要的区别:
<template>
<h2 v-show="showHeading">使用v-show显示的标题</h2>
<h2 v-if="showHeading">使用v-if显示的标题</h2>
</template>
<script>
export default {
data() {
return {
showHeading: true
}
}
}
</script>主要区别:
| 特性 | v-if | v-show |
|---|---|---|
| 渲染方式 | 条件为真时渲染,为假时销毁元素 | 始终渲染,通过CSS的display属性控制显示/隐藏 |
| 初始渲染开销 | 条件为假时开销小 | 始终有渲染开销 |
| 切换开销 | 较大(涉及DOM的创建和销毁) | 较小(仅CSS样式修改) |
| 适用场景 | 条件不经常改变的场景 | 条件频繁改变的场景 |
| 支持的元素 | 任何元素,包括 | 任何元素,但不支持 |
最佳实践:
- 对于频繁切换的元素,使用
v-show - 对于条件不经常改变的元素,使用
v-if
3. 用<template>包裹多个元素
当需要条件渲染多个元素时,可以使用<template>标签来包裹,避免添加额外的DOM元素:
<template>
<template v-if="showContent">
<h3>这是标题</h3>
<p>这是第一段内容</p>
<p>这是第二段内容</p>
<button>点击按钮</button>
</template>
<!-- v-else 也可以使用 template -->
<template v-else>
<p>内容已隐藏</p>
<button @click="showContent = true">显示内容</button>
</template>
</template>
<script>
export default {
data() {
return {
showContent: false
}
}
}
</script>2.4.2 列表渲染v-for深度掌握
v-for指令用于基于源数据多次渲染元素或模板块。
1. 遍历数组
<template>
<!-- 基本用法 -->
<ul>
<li v-for="item in items" :key="item.id">
{{ item.name }}
</li>
</ul>
<!-- 获取索引 -->
<ul>
<li v-for="(item, index) in items" :key="item.id">
{{ index + 1 }}. {{ item.name }}
</li>
</ul>
<!-- 遍历数字 -->
<div>
<span v-for="n in 5" :key="n">{{ n }} </span>
</div>
<!-- 遍历字符串 -->
<div>
<span v-for="char in 'Vue'" :key="char">{{ char }} </span>
</div>
</template>
<script>
export default {
data() {
return {
items: [
{ id: 1, name: '苹果' },
{ id: 2, name: '香蕉' },
{ id: 3, name: '橙子' }
]
}
}
}
</script>2. 遍历对象
<template>
<!-- 遍历对象属性 -->
<ul>
<li v-for="value in user" :key="value">
{{ value }}
</li>
</ul>
<!-- 获取属性名和索引 -->
<ul>
<li v-for="(value, key, index) in user" :key="key">
{{ index }}. {{ key }}: {{ value }}
</li>
</ul>
</template>
<script>
export default {
data() {
return {
user: {
name: '张三',
age: 25,
email: 'zhangsan@example.com'
}
}
}
}
</script>3. key属性的重要性原理分析
key属性是Vue列表渲染中的重要属性,它用于帮助Vue识别列表中哪些项是被修改、添加或移除的。
<template>
<!-- 正确使用key -->
<ul>
<li v-for="item in items" :key="item.id">
{{ item.name }}
</li>
</ul>
<!-- 错误示例:使用索引作为key -->
<ul>
<li v-for="(item, index) in items" :key="index">
{{ item.name }}
</li>
</ul>
</template>key属性的作用:
虚拟DOM diff算法:
- Vue使用虚拟DOM来提高渲染性能
- 当列表数据变化时,Vue会对比新旧虚拟DOM树
key属性帮助Vue识别元素的唯一性,从而更高效地更新DOM
列表更新优化策略:
- 当使用唯一的
key时,Vue可以:- 复用已存在的元素
- 只更新变化的元素
- 正确地移动元素位置
- 当使用索引作为
key时,Vue无法正确识别元素,可能导致性能问题和bug
- 当使用唯一的
最佳实践:
- 总是为
v-for提供key属性 - 使用唯一的、稳定的标识符作为
key(如id、uuid等) - 避免使用索引作为
key,尤其是当列表可能被修改(添加、删除、排序)时
2.4.3 数组更新检测的注意事项
Vue能够检测到数组的变化,但有一些注意事项需要了解。
1. 变更方法 vs 替换数组
Vue包装了数组的变更方法,使得它们能够触发视图更新:
// 这些方法会改变原数组,Vue会检测到变化
export default {
data() {
return {
items: [1, 2, 3]
}
},
methods: {
updateArray() {
// 变更方法
this.items.push(4) // 添加元素
this.items.pop() // 删除最后一个元素
this.items.shift() // 删除第一个元素
this.items.unshift(0) // 在开头添加元素
this.items.splice(1, 1, 5) // 替换元素
this.items.sort() // 排序
this.items.reverse() // 反转
},
replaceArray() {
// 替换数组(不会改变原数组)
this.items = this.items.filter(item => item > 1) // 过滤
this.items = this.items.map(item => item * 2) // 映射
this.items = [...this.items, 4] // 展开运算符
}
}
}变更方法:修改原数组,会触发视图更新
- push()
- pop()
- shift()
- unshift()
- splice()
- sort()
- reverse()
替换方法:返回新数组,需要将新数组赋值给原数组
- filter()
- map()
- slice()
- concat()
- reduce()
2. 响应式数组的限制与解决方案
Vue无法检测到以下数组操作:
通过索引直接修改元素:
this.items[0] = 'new value' // 不会触发更新修改数组长度:
this.items.length = 0 // 不会触发更新
解决方案:
使用Vue.set()方法:
// 引入Vue import Vue from 'vue' // 修改元素 Vue.set(this.items, 0, 'new value') // 或使用this.$set this.$set(this.items, 0, 'new value')使用splice()方法:
// 修改元素 this.items.splice(0, 1, 'new value') // 修改长度 this.items.splice(0)替换整个数组:
// 修改元素 this.items = [...this.items.slice(0, 0), 'new value', ...this.items.slice(1)] // 修改长度 this.items = []
本章小结
在本节中,我们学习了Vue的条件渲染和列表渲染:
条件渲染指令:
v-if、v-else-if、v-else用于条件性地渲染元素v-show用于通过CSS控制元素显示/隐藏- 使用
<template>包裹多个元素进行条件渲染 v-if和v-show的性能对比和最佳实践
**列表渲染
v-for**:- 遍历数组、对象、数字和字符串
key属性的重要性和最佳实践- 虚拟DOM diff算法的工作原理
- 列表更新优化策略
数组更新检测:
- 变更方法和替换方法的区别
- 响应式数组的限制
- 解决方案:Vue.set()、splice()和数组替换
掌握这些内容对于构建动态的Vue应用至关重要,它们是Vue开发中的基础功能。