Contents

Vue computed 無法觸發原因

這篇是我自己踩雷後重新理解 computed 的筆記。以前會以為只要 computed 裡面有依賴的資料變了,它就一定會自動執行;但 Vue 的 computed 其實不是這樣工作的。

view 或者 methods 中有没有用到 pages,如果没有用到,那么是不会触发 computed 的

computed 的核心觀念

computed 本質上比較像是「帶快取的 getter」。它不是 watch,也不是事件監聽器,不會因為相依資料一改就主動做事;而是當畫面或程式真的去讀取這個 computed 屬性時,Vue 才會評估要不要重新計算。

所以最重要的一句話就是:

如果沒有地方使用到這個 computed,它就不會幫你執行。

為什麼會誤會

很多人第一次接觸 Vue,會把 computed 想成「資料變動時自動觸發邏輯」。但這其實比較接近 watch 的思維。

computed 比較像這樣:

  1. 有人讀取它。
  2. Vue 發現相依值改過。
  3. 重新執行 getter。
  4. 回傳新結果。

如果沒有第 1 步,後面根本不會發生。

最常見的踩雷場景

像下面這種寫法,很容易讓人以為 fullName 會自己跑:

1
2
3
4
5
computed: {
	fullName() {
		return this.firstName + ' ' + this.lastName;
	}
}

但如果 template、method、其他 computed 都沒有用到 fullName,那這個 getter 不會被執行。

我這次踩雷的背景

我當時剛好搭配 monaco-editor 這類外部元件使用。它本身不是直接走 Vue 的 template/data binding 流程,而是比較偏事件驅動。結果我用事件改 Vue 的值,卻期待 computed 自己做後續動作,最後就卡了幾個小時。

這時才回頭理解,問題不是 Vue 沒偵測到資料,而是我根本沒有在 view 或 method 中真正使用到那個 computed 結果。

什麼時候該用 computed

我現在會這樣判斷:

  1. 只是把既有資料整理成「給畫面顯示」的結果,用 computed。
  2. 需要在資料變動時主動執行副作用,用 watch。
  3. 只是某個按鈕點下去才需要算一次,用 method。

這三個混掉就很容易寫出看似合理、實際卻不會動的程式。

如果是外部 JS 元件整合

如果你整合的是像 editor、地圖、圖表這類外部元件,我覺得比較實際的方向有:

  1. 在 method 中明確呼叫更新函式。
  2. 用 watch 監看資料後同步到外部元件。
  3. 把外部元件包成真正的 Vue 元件,讓資料流更一致。

我自己後來也覺得,這種情境單靠 computed 很常不夠直覺。

參考