如何在Vue的v-for循环中添加条件过滤同一数据源?
Vue数组循环添加条件过滤的可行方案与最佳实践
当然可行,下面直接给你两种落地方案,并对比优劣:
方案1:模板内直接结合v-for与v-if
你不需要在每个CTableDataCell上加判断,直接在CTableRow层级加v-if就能实现分组渲染:
<!-- 渲染active为true的人员 --> <CTableRow v-for="person in persons" :key="person.id" v-if="person.active"> <CTableDataCell>{{ person.id }}</CTableDataCell> <CTableDataCell>{{ person.name }}</CTableDataCell> <CTableDataCell>{{ person.age }}</CTableDataCell> </CTableRow> <!-- 渲染active为false的人员 --> <CTableRow v-for="person in persons" :key="person.id" v-if="!person.active"> <CTableDataCell>{{ person.id }}</CTableDataCell> <CTableDataCell>{{ person.name }}</CTableDataCell> <CTableDataCell>{{ person.age }}</CTableDataCell> </CTableRow>
注意:建议把key绑定person.id(唯一值),而不是person.status,避免因重复值导致渲染异常。
这种方案的问题是:数组会被遍历两次,数据量大时会有轻微性能损耗;模板内过滤逻辑重复,后续修改条件需要改两处。
方案2:用Composition API拆分计算属性(推荐)
在脚本层提前把数据源拆分成两个过滤后的数组,模板直接循环拆分结果,这是更规范的做法:
// 组件的script部分(Composition API) import { computed } from 'vue' export default { setup() { const persons = /* 你的原始数据源 */ // 计算属性会自动缓存,只有persons变化时才重新计算 const activePersons = computed(() => persons.filter(p => p.active)) const inactivePersons = computed(() => persons.filter(p => !p.active)) return { activePersons, inactivePersons } } }
模板里直接用拆分后的数组:
<!-- 渲染活跃人员 --> <CTableRow v-for="person in activePersons" :key="person.id"> <CTableDataCell>{{ person.id }}</CTableDataCell> <CTableDataCell>{{ person.name }}</CTableDataCell> <CTableDataCell>{{ person.age }}</CTableDataCell> </CTableRow> <!-- 渲染非活跃人员 --> <CTableRow v-for="person in inactivePersons" :key="person.id"> <CTableDataCell>{{ person.id }}</CTableDataCell> <CTableDataCell>{{ person.name }}</CTableDataCell> <CTableDataCell>{{ person.age }}</CTableDataCell> </CTableRow>
方案对比与最佳实践
- 模板内v-for+v-if:适合临时快速实现、数据量极小的场景,但不够优雅,维护性差。
- 计算属性拆分:逻辑集中在脚本层,模板更简洁;计算属性的缓存机制能优化性能;后续修改过滤条件只需改一处,扩展性更强。这是Vue官方推荐的"关注点分离"实践,把数据处理和视图渲染分开。
另外,不建议在每个CTableDataCell上单独加v-if,这种写法冗余且性能差,完全没必要。
内容的提问来源于stack exchange,提问作者DavidLar
相关产品推荐
相关产品推荐

