• 使用proxy以及Reflect还原vue3中的shallowReactive与reactive响应式的原理


    js还原

    // 1 shallowReactive 与 reactive
    // 浅的劫持,浅的监视,浅的响应式数据 与 reactive(深度响应式)
    
    // 定义一个reactiveHandler处理对象
    const reactiveHandler = {
        // 获取属性值
        get(target,prop){
            console.log('get',prop);
            const result = Reflect.get(target,prop)
            return result
        },
        // 修改属性或者说添加属性
        set(target,prop,value){
            console.log('set',prop,value);
            const result = Reflect.set(target,prop,value)
            return result
        },
        // 删除某个属性
        deleteProperty(target,prop){
            console.log('del',prop);
            const result = Reflect.deleteProperty(target,prop)
            return result
        }
    }
    
    // 定义一个shallowReactive函数,传入目标对象
    function shallowReactive(target){
        // 判断当前的目标对象是不是object类型(对象/数组)
        if(target&&typeof target==='object'){
            return new Proxy(target,reactiveHandler)
        }
        // 如果传入的数据是基本类型数据 直接返回
        return target
    }
    
    // 定义一个reactive函数,传入目标对象
    function reactive(target){
        // 判断当前的目标对象是不是object类型(对象/数组)
        if(target&&typeof target==='object'){
    
            // 对数组或者是对象中所有的数据reactive的递归处理
    
            // 先判断当前的数据是不是数组
            if(Array.isArray(target)){
                target.forEach((item,index)=>{
                    target[index] = reactive(item)
                })
            }else{
            // 再判断当前的数据是不是对象
            // 对象数据也要进行遍历
                Object.keys(target).forEach(key=>{
                    target[key] = reactive(target[key])
                })
            }
    
            return new Proxy(target,reactiveHandler)
        }
        // 如果传入的数据是基本类型数据 直接返回
        return target
    }
    

    引入测试

    <script src="./index.js"></script>
       <script type="text/javascript">
        // 测试 浅响应式对象
        const proxyUser1 = shallowReactive({
            name:'小明',
            car:{
                color:'red'
            }
        })
        // 拦截到了读和写数据
        // proxyUser1.name += '小红'
        // 拦截到了读取数据,没有写数据,因为是浅响应
        // proxyUser1.car.color += '小红'
        // 拦截到了删除数据
        // delete proxyUser1.name
        // 拦截到读取拦截不到删除
        // delete proxyUser1.car.color
        // console.log(proxyUser1);
    
        // 测试深度响应式对象
        const proxyUser2 = reactive({
            name:'小明',
            car:{
                color:'red'
            }
        })
        // 拦截到了读和写
        // proxyUser2.name += '小红'
        // 拦截到了读和写
        // proxyUser2.car.color += '小红'
        // 拦截了删除
        // delete proxyUser2.name
        // 拦截到了读和删除
        // delete proxyUser2.car.color
        // console.log(proxyUser2);
    </script>
    
  • 相关阅读:
    Centos开启FTP及用户配置
    mysql update from 子查询
    sql server 查询表某个字段不重复数据
    ASP.NET 获取来源网站的网址,获取上一网页的网址,获取来源网页的URL,获取上一网页的URL
    Warning: Invalid argument supplied for foreach()
    不支持关键字: “userid”。
    apache301重定向设置
    service httpd restart失败解决方法(小记)
    JavaWeb(一)
    jquery中filter的用法
  • 原文地址:https://www.cnblogs.com/xujinglog/p/14647856.html
Copyright © 2020-2023  润新知