# 1. 解构的数据不是响应式的 (toRef/toRefs)
App 为根组件 下面 Home 例子都被此组件引用
// App.vue | |
<template> | |
<div> | |
<home></home> | |
</div> | |
</template> | |
<script> | |
import Home from "./Home.vue"; | |
export default { | |
components: { | |
Home, | |
}, | |
}; | |
</script> | |
<style scoped> | |
</style> |
// Home.vue | |
<template> | |
<div> | |
<!-- --> | |
<h2>{{ name }}-{{ age }}</h2> | |
<button @click="changeAge">修改age</button> | |
</div> | |
</template> | |
<script> | |
import { reactive } from "vue"; | |
export default { | |
setup() { | |
const info = reactive({ name: "Neko", age: 16 }); | |
// 注意这里可以解构,但是解构的数据不是响应式的! | |
let { name, age } = info; | |
const changeAge = () => { | |
// 这里是解构后的 age, 渲染的页面没有发送变化,但是数据已经发送了改变 | |
age++; | |
console.log("解构的age:", age); | |
console.log("原对象:", info); | |
}; | |
return { | |
name, | |
age, | |
changeAge, | |
}; | |
}, | |
}; | |
</script> | |
<style scoped> | |
</style> |
参考结果:
# 2. 使用 toRef 对某一个属性进行响应式
// Home.vue | |
<template> | |
<div> | |
<!-- --> | |
<h2>{{ name }}-{{ age }}</h2> | |
<button @click="changeAge">修改age</button> | |
</div> | |
</template> | |
<script> | |
import { reactive, toRef } from "vue"; | |
export default { | |
setup() { | |
const info = reactive({ name: "Neko", age: 16 }); | |
// 使用 toRefs 包裹住 info 再解构,使得数据变成响应式! | |
let { name } = info; | |
// 这里不需要要解构,之间用变量接收就 OK~ | |
let age = toRef(info, "age"); // 第一个参数是对象名,第二个则是对象里的属性 | |
const changeAge = () => { | |
// 这里和 ref 一样,应使用 value 来获取,并对 age.value++ | |
age.value++; | |
console.log("解构的age:", age); | |
console.log("原对象:", info); | |
}; | |
return { | |
name, | |
age, | |
changeAge, | |
}; | |
}, | |
}; | |
</script> | |
<style scoped> | |
</style> |
参考结果:这里它们的引用地址也是一样的!
# 3. 使用 toRefs 使数据变成响应式
<template> | |
<div> | |
<!-- --> | |
<h2>{{ name }}-{{ age }}</h2> | |
<button @click="changeAge">修改age</button> | |
</div> | |
</template> | |
<script> | |
import { reactive, toRefs } from "vue"; | |
export default { | |
setup() { | |
const info = reactive({ name: "Neko", age: 16 }); | |
// 使用 toRefs 包裹住 info 再解构,使得数据变成响应式! | |
let { name, age } = toRefs(info); | |
const changeAge = () => { | |
// 这里和 ref 一样,应使用 value 来获取,并对 age.value++ | |
age.value++; | |
console.log("解构的age:", age); | |
console.log("原对象:", info); | |
}; | |
return { | |
name, | |
age, | |
changeAge, | |
}; | |
}, | |
}; | |
</script> | |
<style scoped> | |
</style> |
参考结果:注意原对象里的 age 也发生了改变是因为它们的引用地址也是一样的!
# 4. 总结
-
提问:首先它们应该是什么时候用?
-
要对数据解构时可以用
-
toRef 和 toRefs 包裹的必须都是响应式的对象 (reactive/ref)
-
toRef 可以对某一个对象的某个属性进行响应式
-
toRefs 则是对整个对象进行响应式