ref和reactive用哪个?

ref和reactive用哪个?

1.🤖GPT🤖:ref和reactive用哪个根据数据类型而定

ref 用于将基本类型的数据(如字符串、数字,布尔值等)转换为响应式数据。使用 ref 定义的数据可以通过 .value 属性访问和修改。

reactive 用于将对象转换为响应式数据,包括复杂的嵌套对象和数组。使用 reactive 定义的数据可以直接访问和修改属性。

因此,根据使用场景的不同,选择使用 ref 还是 reactive 是有区别的:

  • 如果你只需要处理基础类型的数据,例如字符串、数字、布尔值等,可以使用 ref。
  • 如果你需要处理复杂的嵌套对象或数组,可以使用reactive。

当然,在实际开发中,你也可以同时使用 ref 和 reactive,根据需要选择相应的 API 进行操作。例如,可以使用 ref 来处理单个数据,而使用 reactive 来处理包含多个数据的对象或数组。

2.👉我👈:推荐ref一把梭

reactive 和 ref 对比

2.1前提知识:

2.1.1. ref既能声明基本数据类型,也能声明对象和数组;

Vue 提供了一个 ref() 方法来允许我们创建可以使用任何值类型的响应式 ref

javascript 复制代码
//对象
const state = ref({})
//数组
const state2 = ref([])
2.1.2. reactive失去响应的情况:

reactive一时爽,使用不恰当的时候失去响应泪两行,开开心心敲代码过程中,会感叹!!咦?怎么不行?为什么这么赋值失去响应了? 辣鸡reactive!!! 我要用 ref 👉👉yyds

1. 给响应式对象的字面量赋一整个普通对象/reactive对象

通常在页面数据回显时,需要将AJAX请求获取的对象直接赋值给响应式对象,如果操作不当就导致reactive声明的对象失去响应

赋值一个普通对象

js 复制代码
let state = reactive({ count: 0 })
//这个赋值将导致state失去响应
state = {count: 1}

赋值一个reactive对象

如果给reactive的响应式对象赋值普通对象会失去响应,那么给它赋值一个reactive的响应式对象不就行了吗?下面试试看

html 复制代码
<template>
	{{state}}
</template>    

<stcirpt setup>
	const state = reactive({ count: 0 })
	//nextTick异步方法中修改state的值
	nextTick(() => {
		//并不会触发修改DOM  ,说明失去响应了
		state = reactive({ count: 11 });
	});
</stcirpt>

在nexTick中给state赋值一个reactive的响应式对象,但是DOM并没有更新!

解决方法:

不要直接整个对象替换,对象属性一个个赋值

js 复制代码
let state = reactive({ count: 0 })
//state={count:1}
state.conut = 1 

使用ref定义对象

个人推荐,非必要不用reactive

js 复制代码
let state = ref({ count: 0 })
state.value={count:1}
2.将响应式对象的属性-赋值给变量(断开连接/深拷贝)

这种类似深拷贝不共享同一内存地址了,只是字面量的赋值;对该变量赋值也不会影响原来对象的属性值

js 复制代码
let state = reactive({ count: 0 })
//赋值
// n 是一个局部变量,同 state.count
// 失去响应性连接
let n = state.count
// 不影响原始的 state
n++
console.log(state.count) //0 

有人就说了,既然赋值对象的属性,那我赋值一整个对象不就是浅拷贝了吗?那不就是上面说的给响应式对象的字面量赋一整个普通对象/reactive对象这种情况吗?这种是会失去响应的

3.直接解构时

直接解构会失去响应

解构ref声明的响应式对象也会失去响应

js 复制代码
let state = reactive({ count: 0 })
//普通解构count 和 state.count 失去了响应性连接
let { count } = state 
count++ // state.count值依旧是0

使用toRefs解构不会失去响应

js 复制代码
const state = reactive({ count: 0 })
//使用toRefs解构
let { count } = toRefs(state)
count++ // state.count值改变为1
4.传入一个函数时

将reactive声明的响应式对象的参数传入一个函数时,会失去响应

js 复制代码
let state = reactive({ count: 0 })
    
const fn = (count) => {
	// ⚠️ 这里的 count 是一个普通的 number (不是)
	console.log(count)
	// 不能跟踪 state.count 的改变
}
    
//调用该函数,传入响应式对象的参数
fn(state.count)

2.2. ref一把梭

当使用reactive时,如果不了解reactive失去响应的情况,那么使用reactive会造成很多困扰!

推荐使用ref总结原因如下:

reactive只能声明引用数据类型(对象/数组)

  1. reactive在一些情况下会失去响应,这个情况会导致数据回显失去响应(数据改了,dom没更新)
    给响应式对象的字面量赋一整个普通对象,将会导致reactive声明的响应式数据失去响应
html 复制代码
<template>
	{{state.a}}
	{{state.b}}
	{{state.c}}
</template>      
<script>
let state = reactive({ a:1,b:2,c:3 })
onMounted(()=>{
	//通AJAX请求获取的数据,回显到reactive,如果处理不好将导致变量失去响应,
	//回显失败,给响应式数据赋值一个普通对象
	state =  { a:11,b:22,c:333 }
	//回显成功,一个个属性赋值  
	state.a = 11
	state.b = 22
	state.c = 33 
})
</script>

上面这个例子如果是使用ref进行声明,直接赋值即可,不需要将属性拆分一个个赋值

使用ref替代reactive:

html 复制代码
<template>
{{state.a}}
{{state.b}}
{{state.c}}
</template>
​
<script>
let state = ref({ a:1,b:2,c:3 })
onMounted(()=>{
	//回显成功
	state.value =  { a:11,b:22,c:333 }
})
</script>
  1. ref适用范围更大,声明的数据类型.基本数据类型和引用数据类型都行

虽然使用ref声明的变量,在读取和修改时都需要加.value小尾巴,但是正因为是这个小尾巴,我们review代码的时候就很清楚知道这是一个ref声明的响应式数据。

相关推荐
静西子19 分钟前
Vue3路由
前端·javascript·vue.js
J总裁的小芒果20 分钟前
vue3 全局定义动态样式
前端·javascript·vue.js
whalekv23 分钟前
10月25日
前端·javascript·vue.js
xuelong-ming28 分钟前
uniapp vue3 点击跳转外部网页
vue.js·uni-app
麦麦大数据7 小时前
F036 vue+flask中医热性药知识图谱可视化系统vue+flask+echarts+mysql
vue.js·python·mysql·flask·可视化·中医中药
技术钱7 小时前
vue3前端解析excel文件
前端·vue.js·excel
韩立学长8 小时前
【开题答辩实录分享】以《智慧校园勤工俭学信息管理系统的设计与实现》为例进行答辩实录分享
vue.js·spring boot·微信小程序
@PHARAOH8 小时前
HOW - localstorage 超时管理方案
前端·javascript·vue.js
DokiDoki之父9 小时前
前端速通—Vue_简介 & 第一个Vue程序 & el:挂载点 & data:数据对象 & Vue指令
javascript·vue.js·ecmascript
Crystal32811 小时前
app里video层级最高导致全屏视频上的操作的东西显示不出来的问题
前端·vue.js