Vue3 —— reactive 全家桶及源码学习

  • 该文章是在学习 小满vue3 课程的随堂记录
  • 示例均采用 <script setup>,且包含 typescript 的基础用法

前言

上一篇学习了 ref 全家桶,在此基础上一起学习下 reactive 全家桶

一、reactive 对比 ref

  • ref 可以接收 所有类型reactive 只能接收 object类型(array、object、Map、Set)
  • ref 在取值和赋值时都要通过 .valuereactive不需要
  • reactive 不能直接整体赋值,因为它是通过 proxy 创建的响应式对象,直接赋值会 破坏响应式
    • 解决方案 1:可以 调用一些原生操作,比如 数组可用 push、pop 等去修改
    • 解决方案 2:外面再包上一层

① 创建

import { reactive } from "vue";

// object类型
const form = reactive({
  name: "xiaoman",
  age: 18,
});

// array类型
const list = reactive<string[]>([]);

② 修改

// 错误。直接整体赋值会破坏响应式
// list = ["a", "b", "c"];

// 可以通过原生方法去操作数据,不会破坏响应式
setTimeout(() => {
  const res = ["jay chou", "jolin"];
  list.push(...res);
}, 1000);

// 或者在外面包一层,这样对 obj.list 就可以整体赋值了
const obj = reactive<{ list: string[] }>({
  list: [],
});
setTimeout(() => {
  obj.list = ["a", "b", "c"];
}, 2000);

二、将 reactive 的值 设置为 readonly

  • 设置为 readonly 后不可修改
  • 修改 reactive 源数据,readonly 的值也会受影响
const info = reactive({
  name: "xiaoman",
});
const rd = readonly(info);

// 设置为 readonly 后不可修改
// rd.name = 'daman'

// 但是可以修改它的源数据
info.name = "blue";
console.log("修改源数据,readonly的值也会受影响", info, rd);

可以看到,两者的值都被修改了:

在这里插入图片描述

三、shallowReactive

  • 与上一篇 ref 全家桶 中 shallowRef 十分相似,都是浅层的响应式
  • 修改第一层会触发视图更新,修改深层 不会触发视图更新
  • 有其他触发视图更新的操作,也会顺带将其更新

① reactive 是深层的响应式,视图会立刻更新

const obj2 = reactive({
  foo: {
    bar: {
      name: "xiaoman",
    },
  },
});
setTimeout(() => {
  obj2.foo.bar.name = "blue222222222";
}, 1000);

在这里插入图片描述

② shallowReactive 是浅层的响应式

const obj3 = shallowReactive({
  foo: {
    bar: {
      name: "xiaoman",
    },
  },
});

1、修改浅层才会触发响应式,会立刻更新:

setTimeout(() => {
  obj3.foo = {
    bar: {
      name: "小满",
    },
  };
}, 1000);

2、修改深层可以打印到新值,但视图不会立刻更新:

setTimeout(() => {
  // 修改深层不会触发更新
  obj3.foo.bar.name = "blue3333333333";
  console.log("obj3", obj3); // 打印成功,但是视图不会更新
}, 1000);

控制台:

在这里插入图片描述

视图:

在这里插入图片描述

3、会被其他有视图更新的操作,顺带着一起更新掉

setTimeout(() => {
  // 修改深层不会触发更新
  obj3.foo.bar.name = "blue3333333333";
  console.log("obj3", obj3);
  
  obj2.foo.bar.name = "blue555555"; // obj2 是 reactive,触发更新视图
}, 1000);

在这里插入图片描述

四、源码学习

主要关注 createReactiveObject 函数的逻辑

在这里插入图片描述
学习笔记:

/**
 *
 * 1、reactivity.d.ts中,关于 reactive 的类型定义:
 * 
 *    export declare function reactive<T extends object>(target: T): UnwrapNestedRefs<T>;
 *    
 * 	  其中 T extends object:即只能传入 object 的子类型
 * 
 * 2、reactivity.cjs.prod.js中,
 * 
 *      function reactive(target) {
          if (isReadonly(target)) {
            return target;
          }
        .....
        
 *      即:reactive 如果传入只读类型的,会直接返回
 *          
 *   3、createReactiveObject 函数中,
 *     - 若传入的不是 object 类型,会抛出警告(dev环境)并直接返回;
 *     - 若传入的是被 proxy 代理过的(并且不是为了将其变为只读),也会直接返回
 *     - 如果能从缓存中找到,则直接返回(weakMap)
 *     - 如果在白名单中,也会直接返回,例如 __skip__(后面会讲的 markRaw 处理过的会加一个 __skip__,会跳过proxy代理 )
 *     - 如果以上条件都没触发,就会进行 proxy代理
 *
 */

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/69373.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

3分钟自建查分系统?现在每个人都可以实现了

学生成绩查询系统在现代教育管理中扮演着重要的角色&#xff0c;它不仅可以方便学生和家长查询成绩&#xff0c;也能帮助老师更好地管理和分析学生的学业表现。作为一名教师&#xff0c;了解如何制作学生成绩查询系统是提高教学效率和管理学生成绩便利性的关键。 在制作学生成…

数据结构笔记--链表经典高频题

目录 前言 1--反转单向链表 2--反转单向链表-II 3--反转双向链表 4--打印两个有序链表的公共部分 5--回文链表 6--链表调整 7--复制含有随机指针结点的链表 8--两个单链表相交问题 前言 面经&#xff1a; 针对链表的题目&#xff0c;对于笔试可以不太在乎空间复杂度&a…

深度学习之用PyTorch实现逻辑回归

0.1 学习视频源于&#xff1a;b站&#xff1a;刘二大人《PyTorch深度学习实践》 0.2 本章内容为自主学习总结内容&#xff0c;若有错误欢迎指正&#xff01; 代码&#xff08;类比线性回归&#xff09;&#xff1a; # 调用库 import torch import torch.nn.functional as F#…

手把手教你快速实现内网穿透

快速内网穿透教程 文章目录 快速内网穿透教程前言*cpolar内网穿透使用教程*1. 安装cpolar内网穿透工具1.1 Windows系统1.2 Linux系统1.2.1 安装1.2.2 向系统添加服务1.2.3 启动服务1.2.4 查看服务状态 2. 创建隧道映射内网端口3. 获取公网地址 前言 要想实现在公网访问到本地的…

【CSS】说说响应式布局

目录 一、是什么 二、怎么实现 1、媒体查询 2、百分比 3、vw/vh 4、小结 三、总结 一、是什么 响应式设计简而言之&#xff0c;就是一个网站能够兼容多个终端——而不是为每个终端做一个特定的版本。 响应式网站常见特点&#xff1a; 同时适配PC 平板 手机等…

MacOS创建NetworkExtension 【保姆级流程】

MacOS创建NetworkExtension (保姆级流程) 因为自己工作中的项目&#xff0c;是运行在macos系统上&#xff0c;其中的一部分功能是通过NetworkExtension来获取系统中的流量来做相应的处理&#xff0c;所以也想自己创建一个NetworkExtension&#xff0c;三天&#xff0c;不知道踩…

Linux系统USB转串口芯片 GPIO使用教程

一、简介 WCH的多款USB转单路/多路异步串口芯片&#xff0c;除串口接口以外&#xff0c;还提供独立的GPIO接口&#xff0c;各GPIO引脚支持独立的输出输入&#xff0c;GPIO功能的使用需要与计算机端厂商驱动程序和应用软件配合使用。各芯片的默认GPIO引脚状态有所区别&#xff…

深入理解机器学习与极大似然之间的联系

似然函数&#xff1a;事件A的发生含着有许多其它事件的发生。所以我就把这些其它事件发生的联合概率来作为事件A的概率&#xff0c;也就是似然函数。数据类型的不同&#xff08;离散型和连续性&#xff09;就有不同的似然函数 极大似然极大似然估计方法&#xff08;Maximum Li…

【逗老师的PMP学习笔记】10、项目沟通管理

目录 一、规划沟通管理1、【关键工具】沟通技术2、【关键工具】沟通模型&#xff08;沟通模式&#xff09;3、【关键工具】沟通方法4、【关键工具】文化意识5、【关键输出】沟通管理计划 二、管理沟通1、【关键工具】会议管理 三、监督沟通 一、规划沟通管理 规划沟通管理是基于…

Java集合知识回顾:从分类到工具类,掌握精髓

文章目录 1. 集合的分类2. Collection 接口3. Map 接口4. 泛型5. Collections 工具类总结 在Java编程世界中&#xff0c;集合是一项极为重要的知识&#xff0c;为我们的程序设计提供了强大的数据结构和处理手段。在本篇文章中&#xff0c;我们将回顾集合的分类以及相关的重要概…

dotNet 之网络TCP

**硬件支持型号 点击 查看 硬件支持 详情** DTU701 产品详情 DTU702 产品详情 DTU801 产品详情 DTU802 产品详情 DTU902 产品详情 G5501 产品详情 ARM dotnet 编程 dotNet使用TCP&#xff0c;可以使用Socket和TcpClient 、TcpListener类 2种&#xff0c;对于高级用户&…

nbcio-boot因升级mybatis-plus到3.5.3.1和JSQLParser 到4.6引起的online表单开发的数据库导入出错解决

更多功能看演示系统 gitee源代码地址 后端代码&#xff1a; https://gitee.com/nbacheng/nbcio-boot 前端代码&#xff1a;https://gitee.com/nbacheng/nbcio-vue.git 在线演示&#xff08;包括H5&#xff09; &#xff1a; http://122.227.135.243:9888 nbcio-boot因升级…

怎样学会单片机

0、学单片机首先要明白&#xff0c;一个单片机啥也干不了&#xff0c;学单片机的目的是学习怎么用单片机驱动外部设备&#xff0c;比如数码管&#xff0c;电机&#xff0c;液晶屏等&#xff0c;这个需要外围电路的配合&#xff0c;所以学习单片机在这个层面上可以等同为学习单片…

一起学数据结构(3)——万字解析:链表的概念及单链表的实现

上篇文章介绍了数据结构的一些基本概念&#xff0c;以及顺序表的概念和实现&#xff0c;本文来介绍链表的概念和单链表的实现&#xff0c;在此之前&#xff0c;首先来回顾以下顺序表的特点&#xff1a; 1.顺序表特点回顾&#xff1a; 1. 顺序表是一组地址连续的存储单元依次存…

11_Pulsar Adaptors适配器、kafka适配器、Spark适配器

2.3. Pulsar Adaptors适配器 2.3.1.kafka适配器 2.3.2.Spark适配器 2.3. Pulsar Adaptors适配器 2.3.1.kafka适配器 Pulsar 为使用 Apache Kafka Java 客户端 API 编写的应用程序提供了一个简单的解决方案。 在生产者中, 如果想不改变原有kafka的代码架构, 就切换到Pulsar的…

sentinel核心流程源码解析

sentinel的处理槽(ProcessorSlot) 可以说&#xff0c;sentinel实现的各种功能就是由各处理槽完成的 ,ProcessorSlot定义了四个方法&#xff1a; 当进入该处理槽时触发该方法 处理完 entry方法之后触发该方法 退出该处理槽时触发该方法 exit方法处理完成时触发该方法 sentinel的…

【MySQL安装】卸载与安装MySQL 5.7.X版本

最近由于各种原因&#xff0c;需要重新安装MySQL。之前我的版本是8.0版本&#xff0c;现在装的5.7版本。记录一下自己的安装过程。 目录 1、卸载MySQL8.0 2、安装MySQL5.7 1、卸载MySQL8.0 如何彻底卸载MySQL_mysql 完全卸载_m0小麦麦的博客-CSDN博客相信不少小伙伴们在安装…

ddia(3)----Chapter3. Storage and Retrieval

However, first we’ll start this chapter by talking about storage engines that are used in the kinds of databases that you’re probably familiar with: traditional relational databases, and also most so-called NoSQL databases. We will examine two families o…

捕捉时刻:将PDF文件中的图像提取为个性化的瑰宝(从pdf提取图像)

应用场景&#xff1a; 该功能的用途是从PDF文件中提取图像。这在以下情况下可能会很有用&#xff1a; 图片提取和转换&#xff1a;可能需要将PDF文件中的图像提取出来&#xff0c;并保存为单独的图像文件&#xff0c;以便在其他应用程序中使用或进行进一步处理。例如&#xff…

pdf怎么压缩到1m?这样做压缩率高!

PDF是目前使用率比较高的一种文档格式&#xff0c;因为它具有很高的安全性&#xff0c;还易于传输等&#xff0c;但有时候当文件体积过大时&#xff0c;会给我们带来不便&#xff0c;这时候简单的解决方法就是将其压缩变小。 想要将PDF文件压缩到1M&#xff0c;也要根据具体的情…