zoukankan      html  css  js  c++  java
  • Vue3源码系列之ref、toRef及toRefs的实现

    前言
    ref和reactive的区别
    • reactive内部采用的proxy,ref内部采用的是defineProperty
    • ref也可以放对象,只是取值的时候需要多取一层,如果是对象用reactive更加合理
    • reactive你如果放普通类型,也就是非对象会直接返回,这个原因可以从我之前的博文中查找
    • ref的出现就是因为reactive处理不了基本类型
     
    Ref核心源码
     
    第一步
    源码目录下创建ref.ts文件,创建ref函数
     
    我们接下来要做的第一步就是将传入的普通类型变成一个对象,核心方法是createRef
     
    插一句,源码写到现在,是不是发现很多方法里面又调其它方法,包了一层,原因就是我们其它的api也可能用到,并且通过传递不同的参数去实现不同的功能。所以说Vue3源码基本上都是高阶函数+科里化
     
    第二步
    createRef方法接收两个参数,value和是否是浅的
     
    它内部需要返回一个实例-RefImpl,把参数传进去
     
    RefImpl类
     
    然后利用类的属性访问器,取值的时候track来进行依赖收集,设置值的时候调用trigger去触发更新
    复用了我们之前写reactive时封装的track和tringger方法
     
    可能有人会问了,我文章开头的时候说ref底层是利用的defineProperty,那在哪里呢?其实我们刚才写的代码经过babel转化成es5代码就是defineProperty
     
    然后我们再去处理下_value
     
    当我们取值时取的就是_value
     
    当我们更新值的时候去比较一下新值和老值是否有变化,如果有变化就把新值作为老值
     
    同时我们还要去把_value给改了,改成newVal,最后再去触发更新
     
    然后再去处理shallow,如果是深度需要把里面的都编程响应式的
     
    在我们设置值的时候也要去考虑一下shallow
     
    此时你是不是就明白了,如果ref传入多层对象,底层也是会去调用reactive去把它变成响应式
     
     
    toRef核心源码
    可以把一个对象的值转化成ref类型
     
    内部也会产生一个实例,它用的类跟ref不是同一个类
     
    ObjectRefImpl类
    相当于我们将某一个key对应的值,转化为ref,就是暴露出一个属性的代理出去,并不会做其它事情,所以这个属性是否是响应式的,取决于代理的对象target是否是响应式的。
     
    toRef的使用场景
    当我们从一个reactive处理过的对象拿出来某个属性进行操作的时候,你去重新给拿出来的这个属性赋值,并不会产生什么效果,因为拿出来的值就仅仅是个字符串,不会是响应式的。所以我们为了防止拿出来的值是个字符串,我们需要用toRef做一层代理,让
     
    假如说我想代理多个呢?toRefs就诞生了,不然你总不能一个一个去代理吧
     
    toRefs核心源码
    参数可能是对象也可能是数组
     
    有时候我们想把reactive处理过的值结构出来,但是结构出来的数据就不是响应式的了,所以我们需要toRefs处理一下,相当于Vue自己写了个对象解构方法
     
    再多唠叨一下toRefs的使用场景
    我们这样做,在模板中必须得state.来取,不太友好,有点麻烦,我想在模板中直接用,这个时候我们用toRefs
    这样我们就可以在模板中直接用了
     
    博主掘金技术社区地址——https://juejin.cn/user/1908407918660871/posts
  • 相关阅读:
    线性表的顺序存储结构
    Arrays数组类使用介绍
    collection各实现类用途建议
    【转】数据结构collection接口和map接口架构图
    java 面向对象特性说明
    文件的输入输出操作IO
    sql 约束用法
    select into 在mysql中失效的替换办法
    inner join 、left join 、right join 和full join的区别
    Tomcat 启动过程
  • 原文地址:https://www.cnblogs.com/tengfeiS/p/15259526.html
Copyright © 2011-2022 走看看