美文网首页
vue双向数据绑定原理

vue双向数据绑定原理

作者: lvyweb | 来源:发表于2021-09-22 10:27 被阅读0次

前置技术点

1、数组reduce()方法
应用场景:下次操作的初始值,依赖于上次操作的返回值

  • 数值的累加计算
 //一个数组的所有项累加
    const arr = [2,3,4,6,2,12,34,56]; 
    //    一般实现方案 
    let total = 0;
    arr.forEach((item) => {
        total += item;
    })
    console.log('total--',total);

    // 数组的reduce方法,会循环当前的数组,侧重于进行“滚雪球”操作
    // 数组.reduce(函数,初始值)
    // 数组.reduce ((上次计算的结果,当前循环的Item项) => {},0)
    // const 累加的结果 = 数组.reduce((上次计算的结果,当前循环的Item项) => {return 上次的结果+ 当前循环的Item项},0)
    const total2 = arr.reduce((val,item)=>{
        return val+ item;
    })
    console.log('total2--',total2);
  • 链式获取对象属性的值

2、发布订阅模式

  1. Dep类
  • 负责进行依赖收集
  • 首先,有个数组,专门用来存放所有的订阅信息
  • 其次,还要提供一个向数组中追加订阅信息的方法
  • 最后,还要提供一个循环,循环触发数组中的每个订阅信息
    注:只要我们为Vue中data数据重新赋值了,这个赋值的动作,会被Vue监听到,
    然后vue要把数据的变化通知每个订阅者,
    接下来,订阅者(DOM元素)要根据最新的数据,更新自己的内容
  1. Watcher 类
  • 负责订阅一些事件

3、 使用object.defineProperty()进行数据劫持
1. 通过get()劫持取值操作
2. 通过set()劫持赋值操作

    //定义一个数据劫持的方法
    function Observe(obj){
        //这是递归的终止条件
        if(!obj || typeof obj!='object') return;
        //通过Object.keys(obj)获取当前obj上的每个属性
        Object.keys(obj).forEach((key) => {
            //当前被循环的key所对应的属性值
            let value = obj[key];
            //当前被循环的key所对应的属性值
            Observe(value);
            //需要为当前的key所对应的属性,添加getter和setter
            Object.defineProperty(obj,key,{
                enumerable: true,
                configurable: true,
                get(){
                    // console.log(`有人获取了${key}的值`);
                    return value;
                },
                set(newVal){
                    value = newVal;
                    Observe(value);
                }
            })
        })
    }

为什么methods对象下的法可以通过this获得data下的属性

  //属性代理
   object.key((this.$data).forEach((key) => {
       object.defineProperty(this,key,{
           enumerable: true,
           configurable: true,
           get(){
               return this.$data[key];
           },
           set(newValue){
               this.$data[key] = newValue;
           }
       })
   }))

对html结构进行模板编译

//对html结构进行模板编译的方法
function Compile(el,vm){
    //获取el对应的DOM元素
    vm.$el = document.querySelector(el);
    
    //创建文档碎片,提高DOM操作的性能
    const fragment = document.createDocumentFragment();
    while ((childNode = vm.$el.firstChild)){
        fragment.appendChild(childNode)
    }

    //进行模板编译
    vm.$el.appendChild(fragment);

 
}
   //负责对DOM模板进行编译的方法
    function replace(){
        //定义匹配插值表达式的正则
        const regMustache = /\{\{\s*(S+)\s*\}\}/

        //证明当前的node节点是一个文本子节点,需要进行正则的替换
        if(node.nodeType === 3){
            //注意:文本子节点,也是一个DOM对象,如果要获取文本子节点的字符串内容,需要调用textContent属性获取
            const text = node.textContent;
            const execResult = regMustache.exec(text);

            console.log(execResult)
            if(execResult){
                const value = execResult[1].split('.').reduce((newObj,k)=>newObj[k],vm);
                node.textContent = text.replace(regMustache,value)
            }
            //终止递归的条件
            return 
        }

        //证明不是文本节点,可能是一个DOM元素,需要进行递归处理
        node.childNodes.forEach((child) => replace(child));
    }

最简单的发布订阅

// 最简单的发布订阅模式


// 收集依赖/收集订阅者
class Dep {
  constructor(){
    //这个subs数组,用来存放所有订阅者的信息
    this.subs = [];
  }
  //向subs数组中,添加订阅者信息
  addSub(watcher){
    this.subs.push(watcher);
  }


// 发布通知的方法
notify(){
  this.subs.forEach((watcher) => watcher.update());
}

}

//订阅者的类

class Watcher{

  // cb回调函数中,记录着当前Watcher如何更新自己的文本内容
// 但是,只知道如何更新自己还不行,还必须拿到最新的数据
// 因此 还需要在new Watcher 期间,把vm 也传递过来(因为vm中保存着最新的数据)
// 除此之外,还需知道,在vm身上众多数据中,哪个数据,才是当前自己需要的数据
// 因此, 必须在new Watcher期间,指定watcher对应的数据名字

  constructor(vm,key,cb){
    this.vm = vm;
    this.key = key;
    this.cb = cb;
  }
  // watcher 的实例,需要有update函数,从而让发布者能够通知我们进行更新
  update(){
    this.cb()
  }
}

const w1 = new Watcher(() =>{
  console.log('我是第一个订阅者')
})

相关文章

  • 深入Vue响应式原理

    1.Vue的双向数据绑定 参考 vue的双向绑定原理及实现Vue双向绑定的实现原理Object.definepro...

  • vue 双向数据绑定

    Vue实现数据双向绑定的原理:Object.defineProperty()vue实现数据双向绑定主要是:采用数据...

  • 前端理论面试--VUE

    vue双向绑定的原理(详细链接) VUE实现双向数据绑定的原理就是利用了 Object.definePropert...

  • Vue实现数据双向绑定的原理

    Vue实现数据双向绑定的原理:Object.defineProperty() vue实现数据双向绑定主要是:采用数...

  • 【转】JavaScript的观察者模式(Vue双向绑定原理)

    关于Vue实现数据双向绑定的原理,请点击:Vue实现数据双向绑定的原理原文链接:JavaScript设计模式之观察...

  • vue面试知识点

    vue 数据双向绑定原理 vue实现数据双向绑定原理主要是:采用数据劫持结合发布订阅设计模式的方式,通过对data...

  • Vue双向数据绑定原理

    剖析Vue实现原理 - 如何实现双向绑定mvvm 本文能帮你做什么?1、了解vue的双向数据绑定原理以及核心代码模...

  • 关于双向绑定的问题

    剖析Vue实现原理 - 如何实现双向绑定mvvm 本文能帮你做什么?1、了解vue的双向数据绑定原理以及核心代码模...

  • 前端面试题:VUE

    1. vue的双向数据绑定实现原理? 2. vue如何在组件之间进行传值? 3. vuex和vue的双向数据绑定...

  • vue

    1、vue的双向数据绑定实现原理 2、vue如何在组件之间进行传值 3、vuex和vue的双向数据绑定有什么冲突 ...

网友评论

      本文标题:vue双向数据绑定原理

      本文链接:https://www.haomeiwen.com/subject/fruwgltx.html