查看: 507|回复: 3

Vue条件渲染:v-if与v-show区别及性能选择

[复制链接]
发表于 7 小时前 | 显示全部楼层 |阅读模式
背景与核心结论
Vue中v-if和v-show都用于条件控制显示,但实现路径不同。v-if是真正的条件渲染:条件为假时元素不进入DOM,切换时创建或销毁DOM及组件实例;v-show是CSS显隐:元素始终渲染并留在DOM中,只切换内联display样式。由此带来初始渲染、切换性能、生命周期和语法限制上的差异。

底层渲染机制
v-if在初始条件为false时,元素不会被渲染到DOM树。条件变为true时,Vue会重新创建该元素及其内部组件、事件监听器,再插入DOM;条件变回false时,会彻底销毁对应DOM节点和组件实例,触发beforeDestroy等生命周期。v-show则无论初始条件是什么,元素始终会被渲染并保留在DOM中,通过内联样式在display:none和display:block(或默认值)之间切换。

性能开销与选型
v-if切换开销大,但初始渲染开销小:初始条件为false时什么都不渲染,只在需要时创建。v-show初始渲染开销大,但切换开销小:一开始就渲染全部元素,后续切换只是修改CSS属性。选型原则是:显示状态需要频繁切换时用v-show,例如Tab切换、折叠面板、密码显隐;显示状态在运行时很少改变时用v-if,例如根据用户权限判断是否显示某个模块、刷新页面后基本不变。

语法限制:v-else链与template
v-if支持配合v-else-if和v-else使用,可以构建完整的条件判断链;v-show不支持v-else或v-else-if,只能单独控制显示或隐藏。v-if可以用在<template>标签上,因为template不是真实DOM节点,v-if负责控制其内部块的整体渲染;v-show不能用在<template>标签上,因为template不会生成真实DOM元素,v-show无法给一个不存在的DOM挂上display:none样式。

直观示例
假设isShow变量为false:
  1. <!-- v-if:审查元素时,这段HTML完全消失,DOM中找不到 -->
  2. <div v-if="isShow">我是 v-if,不存在于 DOM</div>
  3. <!-- v-show:审查元素时,这段HTML存在,只是多了内联样式 style="display: none;" -->
  4. <div v-show="isShow">我是 v-show,只是被藏起来了</div>
复制代码
上面的示例展示了排查时的直观差异:v-if为false时DOM中无该节点;v-show为false时节点仍在,只是被display:none隐藏。理解这一点,有助于定位“元素找不到”和“元素存在但不显示”两类问题。

实践建议
1. 先判断切换频率:高频切换优先用v-show,低频或一次性条件优先用v-if。
2. 需要v-else-if或v-else分支链时,只能用v-if。
3. 需要控制<template>内多个元素整体渲染时用v-if,不要用v-show。
4. 关注生命周期:v-if切换会触发组件销毁和重建,走完整生命周期;v-show从false变为true不会触发生命周期,依赖生命周期做初始化或清理的逻辑要放在正确位置。
5. 排查显示问题时,先看DOM是否存在:不存在多为v-if条件为假;存在但不可见可检查v-show对应的内联display状态。

总结
口诀:频繁切换用v-show,条件分支用v-if;v-if是生是灭,v-show是穿脱马甲。核心差异来自DOM创建或销毁与CSS display切换两条不同实现路径,选型时围绕切换频率、分支需求和template限制判断即可。
回复

使用道具 举报

发表于 3 小时前 | 显示全部楼层

Re: Vue条件渲染:v-if与v-show区别及性能选择

楼主这篇总结得很清楚,尤其是“v-if是生是灭,v-show是穿脱马甲”这个口诀,基本一看就记住了。实际开发中我踩过两个和文中对得上的坑,分享出来给同路人提个醒。 第一个坑是状态丢失。以前做标签页,觉得不常切换就用 v-if 控制内容区,结果切回来表单里填的东西全清空了,因为组件被销毁重建成新实例。后来改成 v-show,切换后状态保留,体验才顺。这个正好印证文中说的生命周期差异,v-if 切换走的是完整的销毁重建流程,依赖组件内部状态或者生命周期做初始化的逻辑,不能想当然地放在被 v-if 控制的那一层。 第二个坑是排查时只看样式不看 DOM。有次明明数据是 false,页面却找到节点,我一度以为赋值没生效。其实用的 v-show,节点一直在,只是挂了个内联 display: none。按楼主文中的排查思路,先看节点在不在,不在多半是 v-if 条件为假,在但看不见就看 v-show 的 display,两步就能定位,比瞎猜省事多了。 另外关于 template 的限制,我也遇到过。想把一组元素整体隐藏,结果对 template 用 v-show 不生效,因为 template 本身不产出真实 DOM,没地方挂 display。换成 v-if 就正常了。原因是 v-if 可以作用在 template 的内部块上,整体控制渲染,这点很多人容易忽略。 总的来说,切换频率、要不要分支链
回复 支持 反对

使用道具 举报

发表于 3 小时前 | 显示全部楼层

Re: Vue条件渲染:v-if与v-show区别及性能选择

楼主这篇总结得很清楚,口诀“频繁切换用 v-show,条件分支用 v-if”也很好记。我自己踩过最多的坑就是第 4 点生命周期:之前有个弹窗用 v-if 控制,每次打开都会重新走一遍 created 和 mounted,结果表单里的初始值和接口请求也跟着重复执行,后来才意识到 v-show 切换根本不会触发生命周期,初始化逻辑放在哪儿很关键。 另外大家经常忽略 template 那个限制,v-show 挂在 template 上确实没意义,因为压根没有真实 DOM 可以挂 display 样式,这个点楼主点出来挺实用的。 排查问题的思路也赞同,先看 DOM 在不在,是“元素找不到”还是“元素存在但不可见”,基本能快速定位是 v-if 还是 v-show 的锅。补充一句个人习惯:如果是权限控制这种几乎不会变的条件,用 v-if 还能顺便减少初始渲染的 DOM 数量;但如果是 Tab 这种来回切的,用 v-show 体验会更顺一些。
回复 支持 反对

使用道具 举报

发表于 3 小时前 | 显示全部楼层

Re: Vue条件渲染:v-if与v-show区别及性能选择

这篇总结得很到位,把 v-if 和 v-show 的差异从底层机制一路讲到选型,尤其是“v-if 是生是灭,v-show 是穿脱马甲”这个口诀,很好记。 我自己平时最容易踩坑的是生命周期那一点:之前有个弹窗用 v-show 控制,结果在里面写初始化请求,第一次打开正常,关闭再打开就不重新请求了,后来才意识到 v-show 切回来根本不会触发生命周期,得改成监听显示状态或者干脆换 v-if。看完这篇更清楚了,这类逻辑确实要按“是否需要重建实例”来选。 另外 template 那个限制也提醒得好,v-show 挂在 template 上没意义,因为根本没有真实 DOM 可以加 display:none。排查的时候先看 DOM 在不在,这个思路很实用,能快速区分是条件没满足还是单纯被隐藏了。 整体逻辑很顺,频率、分支链、template、生命周期、排查顺序这几个判断点基本覆盖了日常选型,收藏了。
回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 注册

本版积分规则

指导单位

江苏省公安厅

江苏省通信管理局

浙江省台州刑侦支队

DEFCON GROUP 86025

Hacking Group 021A

旗下站点

态势感知中心

应急响应中心

红盟安全

联系我们

官方QQ群:112851260

官方邮箱:security#ihonker.org(#改成@)

官方核心成员

关注微信公众号

Archiver|手机版|小黑屋| ( 沪ICP备2021026908号 )

GMT+8, 2026-10-22 22:10 , Processed in 0.042583 second(s), 29 queries , Gzip On.

Powered by ihonker.com

Copyright © 2015-现在.

  • 返回顶部