Vue.js使用computed屬性實(shí)現(xiàn)數(shù)據(jù)自動更新
引言
在Vue.js的世界里,computed屬性就像是你的智能助手,它能自動追蹤變化,幫你快速做出反應(yīng)。想象一下,你在做一道菜,調(diào)料(數(shù)據(jù))一變,味道(界面)立刻跟上。這不僅節(jié)省了你的時(shí)間和精力,還讓整個(gè)烹飪過程更加流暢。
簡而言之,computed屬性讓Vue應(yīng)用更聰明,更高效。接下來,我們來一探究竟。
什么是computed屬性?
computed屬性就像是一個(gè)自動更新的計(jì)算器。在Vue中,你可以有一些數(shù)據(jù),比如你的年齡、你的薪水,然后你可以用這些數(shù)據(jù)來計(jì)算一些新的東西,比如你的退休金。computed屬性就是用來做這種計(jì)算的,而且它會在你原始數(shù)據(jù)變化時(shí)自動重新計(jì)算。
定義computed屬性
在Vue組件里,你可以通過在組件的選項(xiàng)對象中添加computed屬性來定義它。這就像在食譜中添加一個(gè)步驟,告訴Vue當(dāng)某些數(shù)據(jù)變化時(shí),如何重新計(jì)算結(jié)果。
與普通方法的區(qū)別
普通方法就像是一個(gè)手算器,你每次需要結(jié)果時(shí)都得手動去計(jì)算。而computed屬性則像是一個(gè)自動計(jì)算器,它會自動幫你計(jì)算結(jié)果,并且只有當(dāng)你的原始數(shù)據(jù)變化時(shí)才會重新計(jì)算。這樣,你就可以節(jié)省很多手動計(jì)算的時(shí)間和精力。
computed的工作原理
響應(yīng)式依賴追蹤
Vue.js使用了一個(gè)響應(yīng)式系統(tǒng),它能夠追蹤數(shù)據(jù)的變化。每個(gè)組件實(shí)例都有一個(gè)watcher實(shí)例,它會在組件渲染過程中把接觸過的數(shù)據(jù)屬性記錄為依賴。當(dāng)依賴的值發(fā)生變化時(shí),watcher會通知視圖更新。
對于computed屬性,Vue會為每個(gè)屬性創(chuàng)建一個(gè)自己的watcher。當(dāng)你在computed屬性中引用了響應(yīng)式數(shù)據(jù)時(shí),Vue會將這個(gè)數(shù)據(jù)作為一個(gè)依賴加入到這個(gè)watcher中。之后,如果這些依賴的數(shù)據(jù)發(fā)生了變化,watcher會觸發(fā)計(jì)算屬性的重新求值。
緩存機(jī)制
計(jì)算屬性默認(rèn)只有在其響應(yīng)式依賴發(fā)生改變時(shí)才會重新求值。這意味著,如果你有一個(gè)復(fù)雜的計(jì)算過程,它依賴于多個(gè)數(shù)據(jù)屬性,只要這些依賴沒有發(fā)生變化,計(jì)算屬性就不會重新計(jì)算,而是返回上一次計(jì)算的結(jié)果。這種緩存機(jī)制可以避免不必要的計(jì)算,提高應(yīng)用程序的性能。
工作流程
- 初始化: 當(dāng)組件初始化時(shí),Vue會遍歷組件的computed屬性,為每個(gè)屬性創(chuàng)建一個(gè)watcher。
- 依賴收集: 當(dāng)計(jì)算屬性被首次訪問時(shí),Vue會執(zhí)行屬性的getter函數(shù),getter函數(shù)會訪問響應(yīng)式數(shù)據(jù),這時(shí)Vue會將這些數(shù)據(jù)作為依賴加入到計(jì)算屬性的watcher中。
- 變更檢測: 如果計(jì)算屬性的任何一個(gè)依賴發(fā)生了變化,Vue會通知計(jì)算屬性的watcher。
- 重新計(jì)算: watcher會重新運(yùn)行屬性的getter函數(shù)來計(jì)算新的值,并且更新視圖中的相應(yīng)部分。
- 緩存: 如果依賴沒有變化,getter函數(shù)不會重新執(zhí)行,而是直接返回上一次計(jì)算的結(jié)果。
使用場景
計(jì)算屬性適用于復(fù)雜的邏輯計(jì)算,尤其是當(dāng)計(jì)算結(jié)果需要被多個(gè)地方引用時(shí)。由于計(jì)算屬性有緩存機(jī)制,所以當(dāng)計(jì)算開銷較大時(shí),使用計(jì)算屬性可以顯著提高性能。
與methods的區(qū)別
你可能注意到,我們可以在methods中定義一個(gè)方法來實(shí)現(xiàn)與計(jì)算屬性相同的功能。然而,不同之處在于,methods中的方法每次觸發(fā)重新渲染時(shí)都會重新調(diào)用,而計(jì)算屬性只有在依賴的值發(fā)生變化時(shí)才會重新計(jì)算。
基本用法
如何在組件中聲明computed屬性
在Vue組件中,computed屬性是在組件的選項(xiàng)對象中聲明的。你可以把它們想象成組件的一個(gè)小功能,告訴Vue當(dāng)某些數(shù)據(jù)變化時(shí),如何更新界面。
示例代碼
假設(shè)我們有一個(gè)簡單的Vue組件,用來顯示一個(gè)人的名字和年齡。我們還想顯示一個(gè)根據(jù)年齡計(jì)算出來的推薦電影分級。

在上面的代碼中,我們定義了兩個(gè)computed屬性:
fullName:它會將firstName和lastName合并成一個(gè)全名。movieRating:它會根據(jù)age的值來推薦一個(gè)電影分級。
當(dāng)你在模板中使用這些computed屬性時(shí),它們會表現(xiàn)得就像普通的數(shù)據(jù)屬性一樣。例如:

這樣,每當(dāng)firstName、lastName或age發(fā)生變化時(shí),fullName和movieRating就會自動更新,而且它們的結(jié)果會在模板中實(shí)時(shí)顯示出來(響應(yīng)式)。
computed屬性的緩存機(jī)制
緩存機(jī)制
在Vue中,每個(gè)computed屬性都關(guān)聯(lián)著一個(gè)watcher對象,這個(gè)watcher負(fù)責(zé)偵聽屬性依賴的數(shù)據(jù)變化。當(dāng)組件初始化或依賴的數(shù)據(jù)發(fā)生變化時(shí),watcher會執(zhí)行一個(gè)函數(shù)來計(jì)算屬性的值。計(jì)算后的值會被存儲起來,這個(gè)存儲的過程就是所謂的“緩存”。
緩存的好處
- 性能提升:如果計(jì)算屬性依賴的數(shù)據(jù)沒有發(fā)生變化,那么計(jì)算屬性就不會重新計(jì)算,而是直接返回之前存儲的值。這避免了重復(fù)的計(jì)算,尤其是在計(jì)算過程復(fù)雜或耗時(shí)的情況下,可以顯著提高應(yīng)用程序的性能。
- 響應(yīng)速度:由于計(jì)算屬性的結(jié)果是緩存的,用戶界面的更新可以更快地響應(yīng),因?yàn)椴恍枰却?jì)算完成就可以顯示結(jié)果。
- 資源節(jié)省:減少了對CPU和內(nèi)存的不必要使用,這對于依賴于大量數(shù)據(jù)的計(jì)算來說尤其重要。
緩存失效的條件
- 依賴數(shù)據(jù)變化:如果計(jì)算屬性依賴的響應(yīng)式數(shù)據(jù)發(fā)生變化,Vue會檢測到這個(gè)變化,并使緩存失效。這時(shí),計(jì)算屬性會重新計(jì)算并更新結(jié)果。
- 組件更新:當(dāng)組件的狀態(tài)更新,比如數(shù)據(jù)屬性發(fā)生變化,或者組件接收到新的prop,這可能會導(dǎo)致依賴的響應(yīng)式數(shù)據(jù)變化。在這種情況下,相關(guān)的computed屬性緩存也會失效,并重新計(jì)算。
- 手動觸發(fā)更新:在某些情況下,你可能需要手動觸發(fā)computed屬性的更新,比如使用Vue的
this.$forceUpdate方法。這將導(dǎo)致組件及其所有子組件的重新渲染,包括計(jì)算屬性的重新計(jì)算。
緩存機(jī)制的內(nèi)部工作
當(dāng)計(jì)算屬性被訪問時(shí),Vue會做以下幾步:
- 檢查watcher的dirty屬性,這個(gè)屬性表示計(jì)算屬性是否需要重新計(jì)算。
- 如果dirty為true,或者計(jì)算屬性是第一次被訪問,Vue會執(zhí)行屬性的getter函數(shù)來計(jì)算新值,并將結(jié)果存儲起來。
- 執(zhí)行完getter函數(shù)后,將dirty屬性設(shè)置為false,表示計(jì)算屬性現(xiàn)在是“干凈”的,其值已經(jīng)被緩存。
- 當(dāng)計(jì)算屬性的依賴發(fā)生變化時(shí),Vue會將dirty屬性設(shè)置為true,這樣下次訪問計(jì)算屬性時(shí),它會重新計(jì)算。
高級用法
使用計(jì)算屬性進(jìn)行派生狀態(tài)
派生狀態(tài)是指從原始狀態(tài)派生出來的新狀態(tài)。在Vue中,你可以使用computed屬性來創(chuàng)建派生狀態(tài)。這就像是從你的銀行賬戶余額派生出你的可用余額,如果你有貸款,可能還要減去貸款金額。
示例: 假設(shè)你有一個(gè)購物車組件,里面有商品列表和每個(gè)商品的數(shù)量。你可以用computed屬性來計(jì)算總價(jià)。

在這個(gè)例子中,totalPrice是一個(gè)派生的計(jì)算屬性,它根據(jù)商品列表和數(shù)量計(jì)算總價(jià)。
計(jì)算屬性在模板中的使用
computed屬性在模板中的使用和普通數(shù)據(jù)屬性一樣簡單。你可以在模板的任何地方使用它們,就像使用data中的屬性一樣。
示例: 假設(shè)你有一個(gè)顯示用戶信息的組件,你想在模板中顯示用戶的全名和一個(gè)派生的歡迎消息。

在這個(gè)模板中,fullName和totalPrice都是computed屬性,它們可以直接在模板中使用,Vue會自動處理它們的更新和渲染。
通過這種方式,computed屬性不僅幫助你管理派生狀態(tài),還讓你的模板更加簡潔和易于維護(hù)。
計(jì)算屬性的getter和setter
在Vue中,computed屬性可以有g(shù)etter和setter。這就像是你有一個(gè)智能保險(xiǎn)箱,你可以通過一個(gè)密碼(getter)來查看里面的物品,也可以通過另一個(gè)密碼(setter)來添加或更改物品。
何時(shí)使用getter和setter
- 需要對數(shù)據(jù)進(jìn)行轉(zhuǎn)換時(shí):當(dāng)你想在數(shù)據(jù)被讀取或設(shè)置時(shí)進(jìn)行一些轉(zhuǎn)換或驗(yàn)證。
- 需要同步多個(gè)數(shù)據(jù)時(shí):如果你的計(jì)算屬性依賴于多個(gè)數(shù)據(jù)源,使用setter可以幫助你同步這些數(shù)據(jù)。
- 需要在數(shù)據(jù)變化時(shí)執(zhí)行額外操作:例如,當(dāng)用戶更新表單輸入時(shí),你可能需要進(jìn)行驗(yàn)證或其他邏輯處理。
示例代碼展示getter和setter的使用
假設(shè)我們有一個(gè)Vue組件,用于管理用戶的昵稱和真實(shí)姓名。我們希望用戶可以通過昵稱來識別,但同時(shí)我們也希望在內(nèi)部使用真實(shí)姓名。
?編輯
在這個(gè)例子中,nickname是一個(gè)計(jì)算屬性,它有一個(gè)getter和一個(gè)setter。getter返回真實(shí)姓名的第一個(gè)部分作為昵稱,而setter允許用戶通過設(shè)置昵稱來更新真實(shí)姓名。
在模板中,你可以這樣使用這個(gè)計(jì)算屬性:
?編輯
使用v-model指令將輸入框綁定到nickname計(jì)算屬性上。當(dāng)用戶輸入昵稱時(shí),setter會被調(diào)用,更新realName。同時(shí),模板中的realName會自動顯示更新后的真實(shí)姓名。
通過這種方式,getter和setter提供了一種靈活的方式來處理數(shù)據(jù)的讀取和更新,同時(shí)保持了Vue響應(yīng)式系統(tǒng)的優(yōu)勢。
計(jì)算屬性與其他Vue特性的結(jié)合
與watch屬性的比較
computed屬性和watch屬性都是Vue中響應(yīng)式系統(tǒng)的一部分,但它們的用途和行為有所不同:
computed屬性是基于它們的依賴進(jìn)行緩存的,只有當(dāng)依賴項(xiàng)變化時(shí)才會重新計(jì)算。它們通常用于聲明性地描述一個(gè)值是如何根據(jù)組件中其他數(shù)據(jù)計(jì)算得來的。watch屬性用于監(jiān)聽數(shù)據(jù)的變化,并在變化發(fā)生時(shí)執(zhí)行異步操作。watch不提供緩存,每次數(shù)據(jù)變化都會觸發(fā)回調(diào)函數(shù)。
示例:
?編輯
在這個(gè)例子中,computedData會根據(jù)watchedData的變化自動更新,而watchedData的變化也會被watch屬性監(jiān)聽到,并在控制臺中打印出來。
與methods的比較
computed屬性是聲明性的,它們依賴于其他數(shù)據(jù),并且具有緩存機(jī)制。- **
methods**是命令式的,它們可以包含任意的邏輯,并且每次調(diào)用時(shí)都會執(zhí)行。
示例:

在這個(gè)例子中,doubleCount是一個(gè)計(jì)算屬性,它會自動根據(jù)count的變化更新。而increment是一個(gè)方法,每次調(diào)用都會增加count的值。
與props和data的交互
- **
props**是從父組件傳遞到子組件的數(shù)據(jù),它們是只讀的。 - **
data**是組件的本地狀態(tài),可以在組件內(nèi)部被修改。
computed屬性可以依賴于props和data,并且可以用于派生出新的數(shù)據(jù),這些數(shù)據(jù)可以是響應(yīng)式的,也可以用于模板渲染。
示例:

在這個(gè)例子中,combinedMessage是一個(gè)計(jì)算屬性,它結(jié)合了propMessage(來自父組件的props)和message(組件的data),并且可以在模板中使用。
通過這種方式,computed屬性可以與Vue的其他特性無縫結(jié)合,提供強(qiáng)大而靈活的數(shù)據(jù)管理和響應(yīng)式更新機(jī)制。
總結(jié)
Vue的computed屬性是構(gòu)建響應(yīng)式應(yīng)用的強(qiáng)大工具。它們不僅提供了一種聲明性的方式來描述派生狀態(tài),還通過智能緩存機(jī)制優(yōu)化了性能。computed屬性與Vue的其他特性如watch、methods、props和data協(xié)同工作,使得狀態(tài)管理和用戶界面的更新既靈活又高效
以上就是Vue.js使用computed屬性實(shí)現(xiàn)數(shù)據(jù)自動更新的詳細(xì)內(nèi)容,更多關(guān)于Vue computed數(shù)據(jù)自動更新的資料請關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
vue3結(jié)合ts從零實(shí)現(xiàn)vueuse的useRouteQuery方法
這篇文章主要為大家詳細(xì)介紹了如何使用vue3與ts從零實(shí)現(xiàn)一個(gè)類vueuse的useRouteQuery方法,并解決vueuse的useRouteQuery方法存在的一些問題,感興趣的可以了解下2024-03-03
?Electron-Vite?+?Vue?3??項(xiàng)目中實(shí)現(xiàn)流暢觸底加載更多功能
本文介紹在Electron-Vite+Vue3項(xiàng)目中實(shí)現(xiàn)觸底加載的兩種方式:原生滾動監(jiān)聽和vue-infinite-loading庫,下面給大家分享詳細(xì)實(shí)現(xiàn)步驟,感興趣的朋友一起看看吧2025-07-07
通過實(shí)例解析chrome如何在mac環(huán)境中安裝vue-devtools插件
這篇文章主要介紹了通過實(shí)例解析chrome如何在mac環(huán)境中安裝vue-devtools插件,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-07-07
在vue中實(shí)現(xiàn)antd的動態(tài)主題的代碼示例
在需求開發(fā)階段,鑒于項(xiàng)目采用了antd作為基礎(chǔ)組件庫,確保組件外觀與antd一致變得尤為重要,這包括顏色、字體大小及尺寸等樣式的統(tǒng)一,然而,截至當(dāng)前antd-vue尚未實(shí)現(xiàn)這一便捷的CSS變量特性,但理解其背后的實(shí)現(xiàn)機(jī)制后,我們可以自行構(gòu)建這一功能,需要的朋友可以參考下2024-07-07
Vue3實(shí)現(xiàn)點(diǎn)擊按鈕實(shí)現(xiàn)文字變色功能
這篇文章主要介紹了使用Vue3實(shí)現(xiàn)點(diǎn)擊按鈕實(shí)現(xiàn)文字變色功能,文中通過代碼示例給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作有一定的幫助,需要的朋友可以參考下2024-07-07

