reactive()与ref()的区别和连续
ref和reactive都是把变量变成响应式对象
reactive底层使用了泛型约束,只能对引用类型使用。
而ref支持所有的类型,ref取值和赋值都需要 .value
而reactive 不需要
对象
<template><div><form><input type="text" v-model="form.name"><p>{{form.name}}</p><br><input type="text" v-model="form.age"><p>{{form.age}}</p></div>
</template><script setup lang='ts'>
import { reactive, readonly, shallowReactive } from 'vue'type M = {name: string,age: number
}// 对象
let form = reactive<M>({name: 'cc',age: '22'
})</script>
<style scoped></style>
数组
<template><div><form><ul><!-- <li v-for="item in list">{{ item }}</li> --><li v-for="item in list.arr">{{ item }}</li></ul><br><button @click.prevent="add">添加</button></form></div>
</template><script setup lang='ts'>
import { reactive, readonly, shallowReactive } from 'vue'// 数组
let list = reactive<number[]>([])
const add = () => {list.push(1)console.log(list);
}// const add = () => {
// setTimeout(() => {
// let res = ["1", '2', '3']
// // list = res as any
// // console.log(list);
// // 数组是有值的
// // 页面是没有变化的
// // 因为reactiv是 proxy代理的对象
// // 直接赋值会把proxy代理做一个覆盖
// // 不能直接赋值
// // reactive proxy 不能直接赋值 否则破坏响应式对象
// }, 2000);
// }
]]
</script>
reactive是proxy代理的对象,直接赋值会把proxy代理做一个覆盖,不能直接取值
解决方案
1.修改数据结构
let list = reactive<number[]>([])// 解构
const add = () =>{setTimeout(() => {let res = ["1", '2', '3']// 1.数组可以使用push + 解构list.push(...res)console.log(list);// 这时候页面上就会渲染,proxy对象不会被破坏}, 2000);
}
解构获取值res
2.添加一个对象,把数组作为一个属性去解决
let list = reactive<{arr: string[]
}>({arr: []
})
const add = () => {setTimeout(() => {let res = ["1", "2", "3"]list.arr = res}, 2000);
}
readonly
readonly的作用是把reactive对象的所有属性都变成只读的
shaowReactive
<template><div><div>{{ obj2 }}</div><button @click="edit">修改值</button><div>{{ obj3 }}</div><button @click="edit2">修改值</button></div>
</template><script setup lang='ts'>
import { reactive, readonly, shallowReactive } from 'vue'
const obj2 = shallowReactive({foo: {bar: {a: 1}}
})const edit = () => {obj2.foo.bar.a = 2
}const obj3 = reactive({foo: {bar: {a: 1}}
})
const edit2 = () => {obj3.foo.bar.a = 2
}
</script>
<style scoped></style>
这样只会改变reactive的值
shallowReactive的值只会改变第一层的值
而reactive会找到最后一层