阅读 332

《简述Vue 里面 computed 和 watch 的区别》

computed 计算属性

computed 是指计算属性; 它会根据所依赖的数据动态显示新的计算结果, 该计算结果会被缓存起来。computed 的值在 getter 执行后是会被缓存的。如果所依赖的数据发生改变时候, 就会重新调用 getter 来计算最新的结果。

computed 是用来计算出一个值的,

  • 第一,这个值在调用的时候不用加(),
  • 第二,如果依赖不变,会自动缓存,computed 的值就不会重新计算
const vm = new Vue({
  data: {
    message: 'hello'
  },
  template: `
    <div>
      <p>原始字符串:{{message}}</p>
      <p>反转后的字符串:{{reversedMessage}}</p>
    </div>
  `,
  computed: {
    reversedMessage() {
      return this.message.split('').reverse().join('')
    }
  }
}).$mount("#app");
复制代码

watch 监听数据的变化

watch 它是一个对 data 的数据监听回调, 当依赖的 data 的数据变化时, 会执行一个回调函数。在回调中会传入newVal和oldVal两个参数。

new Vue({
  data: {
    message: "",
    name: "ry",
    age: 18
  },
  template: `
    <div>
      <p>个人信息: {{message}}</p>
      <p>年龄: <input type="text" v-model="age" /></p>
    </div>
  `,
  watch: {
    age(newValue, oldValue){
      this.message = this.name + " 今年 " + newValue + " 岁";
    }
  }
}).$mount("#app");
复制代码

第一次页面初始化效果如下: WX20210322-150613@2x.png

如上 watch 有一个特点是:

  • 第一次初始化页面的时候,是不会去执行 age 这个属性监听的,
  • 只有当 age 值发生改变的时候才会执行监听计算。因此我们上面第一次初始化页面的时候,message 属性值默认为空字符串。
  • 那么我们现在想要第一次初始化页面的时候也希望它能够执行 age 进行监听,因此我们需要修改下我们的 watch 的方法,需要引入 handler 方法和 immediate 属性

handler 方法及 immediate 属性

代码如下所示:

new Vue({
  data: {
    message: "",
    name: "ry",
    age: 18
  },
  template: `
    <div>
      <p>个人信息: {{message}}</p>
      <p>年龄: <input type="text" v-model="age" /></p>
    </div>
  `,
  watch: {
    age: {
      handler(newValue, oldValue) {
        this.message = this.name + " 今年 " + newValue + " 岁";
      },
      immediate: true
    }
  }
}).$mount("#app");
复制代码

如上代码, age 属性绑定了一个 handler 方法。其实我们之前的 watch 当中的方法默认就是这个 handler 方法。但是在这里我们使用了immediate: true,含义是: 如果在 watch 里面声明了 age 的话,就会立即执行里面的 handler 方法。如果 immediate 值为 false 的话,果就和之前的一样, 就不会立即执行 handler 这个方法的。因此设置了 mediate:true的话,一次页面加载的时候也会执行该 handler 函数的。即第一次 message 有值。

因此第一次页面初始化效果如下:

WX20210322-150520@2x.png

deep属性

watch 面有一个属性为 deep,含义是:是否深度监听某个对象的值,值默认为 false

new Vue({
  data: {
    obj: {
      message: "",
      name: "ry",
      age: 18
    }
  },
  template: `
    <div>
      <p>个人信息: {{message}}</p>
      <p>年龄: <input type="text" v-model="obj.age" /></p>
    </div>
  `,
  watch: {
    'obj': {
      handler(newValue, oldValue) {
        this.message = this.obj.name + " 今年 " + newValue.age + " 岁";
      },
      immediate: true,
      deep: true
    }
  }
}).$mount("#app");
复制代码

如上代码, 如果不添加 deep: true 的话,当我们在输入框中输入值的时候,改变obj.age 值后,obj 对象中的 handler 函数是不会被执行到的。 Vue 不能检测到对象属性的添加或删除的。它只能监听到 obj 这个对象的变化。

watch 和 computed 的区别是:

相同点:他们两者都是观察页面数据变化的。

不同点

  • computed 只有当依赖的数据变化时才会计算, 当数据没有变化时, 它会读取缓存数据。
  • watch 每次都需要执行函数。watch 更适用于数据变化时的异步操作。
文章分类
前端
文章标签