vue3中的ref、computed、reactive、toRef、toRefs

阅读数:130 评论数:0

跳转到新版页面

分类

html/css/js

正文

一、概述

在vue2中,data函数里返回的值直接为响应式,但在vue3中我们需要使用一些函数才能达到这个效果。

setup函数中拿不到vue的this。

二、常用函数

<template>
  <div id='app'>
    <img alt="vue logo" src="./assets/logo.png">
    <!-- ref对象在模板中引用时,vue可以直接把内部的值展示出来,不需要写count.value -->
    <h1>{{count}}</h1>
    <h1>{{double}}</h1>
    <button @click='increase'>点击</button>
  </div>
</template>
 
<script lang='ts'>
//ref API:是一个函数,输入参数为一个值,返回一个响应式对象
//computed API:是一个函数,输入参数为函数类型,该输入函数中包含咱们需要的值
//reactive:将响应式变量包裹在一起,更加清晰
import {computed, ref,reactive} from 'vue'
 
export default({
  name: 'App', 
 
  /*data(){
    return{
      count: 0
    }
  },
  methods:{
    increase(){
      this.count++
    }
  }*/
 
  // 注意:在vue3中不使用data和methods,可以使用ref函数,完成响应式
  setup(){
    const count = ref(0)    //将0传入,返回一个对象
 
    const double = computed(()=>{
      return count.value*2
    })
    const increase = ()=>{
      count.value++         //通过返回对象的value属性获得响应式的数据
    }
    return{                 //要在外面使用的变量都要先通过return导出,才能使用
      count,
      increase,
      double
    }
  }
});
</script>

1、ref

本质为一个函数,输入参数为一个值,返回响应式的对象。

(1)在js中操作数据时要使用.value

(2)在模板中读取数据不需要.value,可以直接使用

(3)接收的数据类型可以是基本数据类型,也可以是引用数据类型

ref底层使用的是proxy代理函数实现双向绑定。

// 父组件
<template>
	<Son :data="data"/>
</template>
<script setup>
import { ref } from "vue";
let data = ref('hello')
setTimeout(() => {
	data.value = 'how are you doing'
}, 2000)

</script>

// 子组件
<template>
	<div>{{ msg }}</div>
</template>
<script setup>
import { ref } from "vue";
// 接受来自父组件的传参
const props = defineProps({
  data: String,
});
const msg = ref(props.data);

</script>

此时父组件改变 data 的值,子组件 msg 无法响应 data 的变化。

因为 ref 是对传入数据的拷贝,原始值 data 的改变并不影响 msg

但 toRef 是对传入数据的引用,原始值 data 改变会影响 msg

<template>
	<div>{{ msg }}</div>
	<div>{{ data }}</div>
</template>
<script setup>
import { ref, toRefs, toRef } from "vue";
// 接受来自父组件的传参
const props = defineProps({
  data: String,
});
// 方法1:
const msg = toRef(props, 'data');
// 方法2:
const { data } = toRefs(props);

</script>

2、computed

本质为一个函数,输入函数是一个函数,可以将我们需要的值作为输入函数的返回值。

3、reactive

定义一个对象类型的响应式数据(基本数据类型别用它,用ref函数),主要用于嵌套层级比较复杂的数据。

let代理一个对象 = reactive(被代理的对象) 接收一个对象(或数组),返回一个代理器对象(proxy对象),即 let xxx = reactive(value)

注意:在js中操作数据时不需要使用.value,可以直接使用变量

<script setup>
    let arr2 = reactive([111,{name:"xiaozhang",like:["game","study"]}])
    let change6 = ()=> {
        arr2[1].like[0] = "read"
    }
</script>   
 
<template>
  <div>
    <p>{{arr2[1].like[0]}}</p>
    <button @click="change6">change6</button>
  </div>
</template> 
 

4、toRef

转换一个reactive对象中的属性为ref,获取数据值需要加.value

toRef接收两个参数target和attr,target是响应式对象,attr是对象的属性。

import {reactive,toRef} from 'vue'
setup(){
    const obj = reactive({ name: "姜无忧", age: "18" })
    const name = toRef(obj, "name") 
    
    return {
       name 
    }
}

5、toRefs

将reactive对象中的属性都转换ref。使用ES6的解构语法 ,因为一个响应式对象直接解构时,解构后的数据不再具有响应式。

import {reactive,toRefs} from 'vue'
setup(){
    const obj = reactive({ name: "姜无忧", age: "18" })
    const {name,age} = toRefs(obj) 
    
    return {
       name,
       age 
    }
}
 
//或者
import {reactive,toRefs} from 'vue'
setup(){
    const obj = reactive({ name: "姜无忧", age: "18" })
    
    return {
      ...toRefs(obj)
    }
}



相关推荐

一、概述 在vue3中没有$refs这个对象,可以使用如下方法 <template> <div><input type="text" ref="txt1" value="hello" /></div>

ref被用来给元素或子组件注册引用信息,引用信息将会注册在父组件的$refs对象上。如果在普通的DOM元素上使用,引用指向的就是DOM元素,如果用在子组件上,引用就指向组件实例。 <!-- `vm.$

一、computed和watch应用场景 1、computed computed拥有缓存属性,擅长的处理的场景是一个数据受多个数据影响。 2、watch 擅长处理的场景是一个数据影响多个数据,另外可以

最近自己做了一个网站,使用了cdn加速bootstrap和jquery的加载。这里先解释一下什么是cdn。 c

一、生命周期 1、vue2生命周期 beforeCreate #实例初始化之后,进行数据侦听和事件/侦听器的配置之前同步调用 created #实例创建完成后被立即同步调用 beforeMount #

一、使用pnpm新建项目 可以使用npm 或yarn或pnpm来初始化Vite项目 pnpm create vite xxx(项目名称) #选择vue #选择js cd xxx (进入项目目录) #安

一、概述 <script setup> 是在单文件组件(SFC)中使用组合式API的编译时语法糖,解决Vue3.0中setup需要频繁将声明的变量、函数以及import引入的内容通过return向外

<script> export default { setup() { const func1= () => { console.log("func1");

缓存页面主要Jul为了防止重复渲染dom,减少加载时间及性能消耗,提高用户体验。 一、旧版的语法 <keep-alive> <router-view v-if="$route.meta.kee

一、在main.js挂载 import { createApp } from 'vue' import App from './App.vue' import router from './route