news 2026/1/12 21:45:38

Vue基础入门07,深入理解 Vue computed 计算属性:缓存机制与 methods 的核心区别

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Vue基础入门07,深入理解 Vue computed 计算属性:缓存机制与 methods 的核心区别

在 Vue 开发中,我们经常需要根据已有数据处理并返回新的结果,比如对列表进行过滤、拼接字符串、计算数值总和等。此时,computed计算属性和methods方法都能实现这个需求,但很多初学者会疑惑:两者到底有什么区别?什么时候该用 computed,什么时候该用 methods?

这篇文章将从computed的缓存机制入手,深入剖析它与methods的核心差异,帮你彻底搞懂二者的使用场景。

一、先看一个简单的例子

我们先通过一个基础案例,直观感受下computedmethods的表现差异。

假设我们有一个 Vue 实例,里面有firstNamelastName两个数据,需要拼接成完整的姓名:

1. 使用 methods 实现

<template> <div> <p>姓名:{{ getFullName() }}</p> <p>姓名:{{ getFullName() }}</p> <p>姓名:{{ getFullName() }}</p> </div> </template> <script> export default { data() { return { firstName: '张', lastName: '三' } }, methods: { getFullName() { console.log('methods执行了'); return this.firstName + this.lastName; } } } </script>

此时打开控制台,会发现methods执行了被打印了三次—— 因为模板中每次调用getFullName(),方法都会重新执行一次。

2. 使用 computed 计算属性实现

<template> <div> <p>姓名:{{ fullName }}</p> <p>姓名:{{ fullName }}</p> <p>姓名:{{ fullName }}</p> </div> </template> <script> export default { data() { return { firstName: '张', lastName: '三' } }, computed: { fullName() { console.log('computed执行了'); return this.firstName + this.lastName; } } } </script>

这时候控制台只打印了一次computed执行了—— 即使模板中多次引用fullName,计算属性也只执行了一次。

这个差异的根源,就是computed缓存机制

二、computed 的缓存机制:到底是什么?

Vue 的计算属性基于其依赖的响应式数据进行缓存。简单来说:

计算属性会记住它的依赖(比如上面例子中的firstNamelastName),只有当依赖的响应式数据发生变化时,计算属性才会重新计算并更新结果;如果依赖没有变化,每次访问计算属性都会直接返回缓存的结果,不会重新执行函数。

缓存机制的底层逻辑(简易版)

  1. 当 Vue 实例初始化时,会解析计算属性的函数,收集其中依赖的响应式数据(如firstNamelastName)。
  2. 第一次访问计算属性时,执行函数并将结果缓存起来。
  3. 当依赖的响应式数据发生变化时,Vue 会触发依赖更新,清空计算属性的缓存,下次访问时重新计算并缓存新结果。
  4. 如果依赖没有变化,直接返回缓存的结果。

举个例子:依赖变化时的缓存更新

我们给上面的例子加一个按钮,修改firstName

<template> <div> <p>姓名:{{ fullName }}</p> <p>姓名:{{ fullName }}</p> <button @click="changeFirstName">修改姓</button> </div> </template> <script> export default { data() { return { firstName: '张', lastName: '三' } }, computed: { fullName() { console.log('computed执行了'); return this.firstName + this.lastName; } }, methods: { changeFirstName() { this.firstName = '李'; } } } </script>

此时:

  • 页面初始化:打印 1 次computed执行了(缓存结果:张三)。
  • 点击按钮修改firstName为 “李”:依赖变化,打印 1 次computed执行了(重新计算并缓存:李四)。
  • 再次访问fullName:直接返回缓存的 “李四”,不再执行函数。

三、computed vs methods:核心区别

通过上面的例子,我们可以总结出二者的核心差异:

特性computed 计算属性methods 方法
缓存机制基于依赖的响应式数据缓存结果无缓存,每次调用都会重新执行函数
调用方式模板中直接引用(如{{ fullName }}),无需加括号模板中需要加括号调用(如{{ getFullName() }}
返回值要求必须有返回值(因为要缓存结果)可以有返回值,也可以无返回值(如处理事件)
响应式依赖自动追踪依赖的响应式数据不会自动追踪,仅在调用时执行
适用场景数据处理、数据派生(依赖固定数据)事件处理、一次性操作、复杂逻辑(无需缓存)

补充:computed 的 setter 和 getter

计算属性默认只有 getter(取值函数),但也可以设置 setter(赋值函数),实现 “可写的计算属性”:

computed: { fullName: { // getter:取值时执行 get() { return this.firstName + this.lastName; }, // setter:赋值时执行 set(newValue) { const [first, last] = newValue.split(' '); this.firstName = first; this.lastName = last; } } }

此时,我们可以直接给fullName赋值:this.fullName = '王 五',setter 会被触发,自动更新firstNamelastName。而 methods 无法实现这种 “赋值联动” 的效果。

四、什么时候用 computed?什么时候用 methods?

结合缓存机制和使用场景,我们可以给出明确的选择原则:

优先用 computed 的场景

  1. 需要根据已有响应式数据派生新数据:比如拼接字符串、过滤列表(filteredList)、计算数值(totalPrice)等。
  2. 数据会被多次访问:比如模板中多次引用、多个地方使用同一个派生数据,缓存能减少重复计算,提升性能。
  3. 依赖的数据源是固定的响应式数据:计算属性的缓存只有在依赖变化时才会更新,适合这种场景。

优先用 methods 的场景

  1. 处理事件逻辑:比如按钮点击、表单提交等(这是 methods 最常见的用途)。
  2. 执行一次性操作:比如请求接口、操作 DOM、随机数生成(因为随机数不是响应式依赖,computed 无法缓存)。
  3. 复杂逻辑且无需缓存:比如需要传递参数的函数(computed 无法直接接收参数,虽然可以通过闭包实现,但不如 methods 直观)。
  4. 不依赖响应式数据的操作:比如纯逻辑计算,没有依赖的响应式数据,computed 的缓存机制就失去了意义。

注意:computed 不能直接接收参数?

有同学会问:computed 能不能像 methods 一样接收参数?

答案是:默认不能,但可以通过返回函数的方式间接实现,比如:

computed: { getFullName() { // 返回一个函数,接收参数 return (middleName) => { return this.firstName + middleName + this.lastName; } } }

模板中调用:{{ getFullName('小') }}

但这种方式会失去缓存机制—— 因为每次调用都会返回一个新的函数,相当于每次执行都是新的计算,此时 computed 的缓存优势就没了。所以如果需要传递参数,优先用 methods。

五、性能影响:缓存的重要性

在简单场景下,computed 和 methods 的性能差异并不明显,但在复杂计算或大量数据处理的场景下,缓存机制的影响会被放大。

比如,我们有一个包含 1000 条数据的列表,需要过滤出符合条件的项:

// 用computed:只在列表或过滤条件变化时重新计算 computed: { filteredList() { return this.list.filter(item => item.age > 18); } } // 用methods:每次调用都要遍历1000条数据 methods: { getFilteredList() { return this.list.filter(item => item.age > 18); } }

如果模板中多次引用这个过滤后的列表,computed 只需要执行一次过滤,而 methods 需要执行多次,性能差异会非常明显。

六、总结

  1. 缓存是 computed 和 methods 的核心区别:computed 基于响应式依赖缓存结果,methods 无缓存。
  2. 调用方式不同:computed 在模板中直接引用,methods 需要加括号调用。
  3. 使用场景不同
    • computed:适合数据派生、多次访问的场景,利用缓存提升性能。
    • methods:适合事件处理、一次性操作、需要传参的场景。
  4. 不要为了用 computed 而用 computed,如果不需要缓存,methods 反而更简单。

理解了 computed 的缓存机制和二者的区别,你就能在 Vue 开发中做出更合理的选择,写出性能更优、更易维护的代码。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/1/12 11:01:08

项目全过程管理系统工具盘点:9款覆盖立项到验收的全流程管理方案

在企业数字化转型的深水区&#xff0c;项目全过程管理&#xff08;Project Lifecycle Management&#xff09;已成为企业提升运营效率的核心抓手。传统的碎片化工具链往往导致数据孤岛&#xff0c;使得决策者难以获取实时的项目全貌。 本文旨在为企业管理系统选型者提供一份详尽…

作者头像 李华
网站建设 2026/1/7 1:30:47

SFINAE 是技術債:C++20 Concepts 如何讓你的模板程式碼減少 80%

SFINAE 是技術債&#xff1a;C20 Concepts 如何讓你的模板程式碼減少 80%引言&#xff1a;C模板的演進與挑戰C模板自誕生以來一直是該語言最強大的特性之一&#xff0c;它提供了編譯時多態和泛型編程的能力。然而&#xff0c;在長達數十年的發展過程中&#xff0c;開發者們一直…

作者头像 李华
网站建设 2026/1/12 14:11:40

Open-AutoGLM + 边缘计算:打造低延迟农业感知系统的3种架构模式

第一章&#xff1a;Open-AutoGLM 农业物联网适配在现代农业系统中&#xff0c;物联网设备与智能模型的深度融合成为提升生产效率的关键路径。Open-AutoGLM 作为一款支持自动化推理与轻量化部署的语言模型框架&#xff0c;具备良好的边缘计算适配能力&#xff0c;能够有效集成至…

作者头像 李华
网站建设 2026/1/7 19:26:50

Open-AutoGLM自主训练闭环实战(稀缺技术文档首次公开)

第一章&#xff1a;Open-AutoGLM自主学习进化机制Open-AutoGLM 是一种基于大语言模型的自主学习与持续进化框架&#xff0c;旨在实现模型在无显式人工干预下的知识更新、任务优化与能力扩展。其核心机制依托于动态反馈循环、自我评估模块与外部环境交互&#xff0c;使系统能够在…

作者头像 李华
网站建设 2026/1/12 15:56:55

Open-AutoGLM模型推理延迟降低90%?揭秘其背后的轻量化架构设计

第一章&#xff1a;Open-AutoGLM 自动驾驶辅助交互Open-AutoGLM 是一个基于大语言模型的开源框架&#xff0c;专为自动驾驶场景中的多模态人机交互设计。它融合自然语言理解、环境感知与车辆控制指令生成&#xff0c;实现更智能、更安全的驾驶辅助体验。该系统能够解析驾驶员语…

作者头像 李华
网站建设 2026/1/11 10:15:31

springboot车辆管理系统(11552)

有需要的同学&#xff0c;源代码和配套文档领取&#xff0c;加文章最下方的名片哦 一、项目演示 项目演示视频 二、资料介绍 完整源代码&#xff08;前后端源代码SQL脚本&#xff09;配套文档&#xff08;LWPPT开题报告&#xff09;远程调试控屏包运行 三、技术介绍 Java…

作者头像 李华