「Vue computed與methods之差異,以及getter/setter」相關筆記

總結

此篇為參考 Vue.js 官方文件與其他網路資源後,記錄 computed 與 methods 差異、以及 getter/setter 相關筆記

環境

Vue.js: 2.X

筆記

computed

小總結:

reactive dependency

const vm = new Vue({
  data: {
    a: 1
  }
})
// vm.a is reactive

vm.b = 2
// vm.b is NOT reactive

A property must be present in the data object in order for Vue to convert it and make it reactive.

const vm = new Vue({
  data: {
    // declare message with an empty value
    message: ''
  },
  template: '<div>{{ message }}</div>'
})
// set `message` later
vm.message = 'Hello!'

Vue doesn’t allow dynamically adding root-level reactive properties, you have to initialize Vue instances by declaring all root-level reactive data properties upfront, even with an empty value.

小總結:需要由 Vue 監視其內容是否改變的資料,一定要放在 Vue instance 的 data 物件中

computed VS methods

參考Method vs Computed in Vue 討論串中 Giulio Bambini 的答案,可以觀察到「即使互動的按鈕僅更新到data.a的值,addToBmethod也會被呼叫」 而 computed property 依存的變數若沒有被更新,computed property 會直接回傳 cache 中的值,不會進行重運算

getter/setter (JavaScript Accessors)

<div id="demo">{{ fullName }}</div>
data: {
  firstName: 'Hello',
  lastName: 'World',
  fullName: 'Hello World'
},
computed: {
  fullName: {
    // getter
    get: function () {
      return this.firstName + ' ' + this.lastName
    },
    // setter
    set: function (newValue) {
      var names = newValue.split(' ')
      this.firstName = names[0]
      this.lastName = names[names.length - 1]
    }
  }
}

MDN 對 getter/setter 的定義:

W3Schools 的範例

const obj = { counter : 0 }

// Define setters
Object.defineProperty(obj, "reset", {
  get: function () { this.counter = 0 }
})
Object.defineProperty(obj, "increment", {
  get: function () { this.counter++ }
})
Object.defineProperty(obj, "decrement", {
  get: function () { this.counter-- }
})
Object.defineProperty(obj, "add", {
  set: function (value) { this.counter += value }
})
Object.defineProperty(obj, "subtract", {
  set: function (value) { this.counter -= value }
})

obj.reset         // { counter : 0 }
obj.add = 5       // { counter : 5 }
obj.subtract = 1  // { counter : 4 }
obj.increment     // { counter : 5 }
obj.decrement     // { counter : 4 }

參考文件