【vue】响应式原理

vue源码解析

目标

  • 深入理解vue底层原理
  • 手写vue核心部分

知识要点

vue工作机制

在这里插入图片描述

  • 第一步,将data添加到响应式系统中;
    • new Observer( this.$data ):内部将Vue实例对象的属性遍历执行 Object.defineProperty(this,key,{set(newVal){},get(){}});
    • set(newVal){ val = newVal;dep.notify() }:用于监听属性值的改变,并通知该属性的所有订阅者;
    • get(){ dep.addSub(Dep.target) }:用于监听属性值被获取,并将订阅者(Watcher实例)push到订阅者数组中,由订阅者实例化对象时引发;
  • 第二步,代理this.$data数据
Object.keys(this.$data).forEach(key=>{
	this._proxy(key)
})
  • 第三步,处理el;

    • new Compiler(this.$el,this)// this:vue实例
    • 编译模板,当正则找到{{msg}}中的属性名时,new Watcher(node,name,this.vm)//当前文本节点,对应的属性名msg,vue实例;
    • 在节点中找到属性名–>触发创建Watcher实例–>触发属性get() -->添加订阅者到该属性的订阅者数组;
  • 总结:

    • Observer:用于能监听data属性被get或被set,让每个属性成为发布者,并提供一个subs数组存放订阅者;
    • Compiler:用于编译模板,找到模板中data属性的使用节点,将节点变成订阅者,并将属性值渲染到视图中;

  • template->ast->render->vdom
    template()编译分为三个阶段:

    parse(作语法分析):使用正则解析template中vue指令、变量,形成ast抽象语法树;

    optimize(使最优化):标记静态节点,在diff算法时略过,优化性能

    generate(产生):把ast抽象语法树转化为渲染函数render function

vue响应式原理


Object.keys(对象):遍历对象所有可枚举的属性名,以数组形式返回;

Constructor(构造函数):是在对象创建或者实例化时候被调用的方法,通常使用该方法来初始化数据成员和所需资源。

  • class Vue{}:实现遍历给所有data属性设置get、set方法,无论属性是否在组件中被用到。
  • class Dep{}:为所有属性分别创建一个空数组deps,用于(push)存放组件中的所有使用到该属性的元素即(所有Watcher实例);一个属性对应一个Dep实例对应一个或多个Watcher实例(一个组件元素)。
    • 与get(通过this.$data.test触发)关联:get执行时,接收并存放外部发来的该属性所对应的组件元素订阅信息。(一般没在页面中使用就不调用get方法,同时也不必为其产生Watcher实例);
    • 与set方法(通过this.$data.test=’'触发)关联:set方法被执行时,接收该属性改变,遍历deps发布给该属性所有的watcher;
  • claa Watcher{}:在编译时,将组件中使用到某个属性的某个元素传递给Dep做订阅,接受Dep发布的信息,通知视图更新自身这个元素所使用的这个属性,所以内部定义了updated方法。

依赖收集与追踪


先给每个data属性创建一个Dep实例并设置get、set方法,当方法被执行时,Dep、Watcher就起作用了。get的执行与watcher实例的创建都要在初始编译过程触发,set在更改数据后再编译时触发。

执行get方法时:‘外界’会产生一个Watcher实例,将Watcher实例传到了Dep实例中存放起来,所以get方法必须执行,要不然无法记录订阅者。

执行set方法:便会执行Dep实例中的通知方法notify(),这个方法会遍历deps中所有Watcher实例并让他们都执行更新操作update(),最后每个Watcher实例再各自去通知自己的视图做改变。

编译compile


把特殊的符号编译,收集起来创造Watcher。

vue编译过程是怎样的?

首先,什么是编译,为什么编译,怎么实现
vue模板语句html不识别,通过编译的过程,可以进行依赖收集,将data数据模型与视图之间绑定关系,模型变化可以通知依赖进行更新,做到模型驱动视图的变化。

双向绑定

v-model,在编译时解析,给model所属的节点加input事件监听,通过input事件将输入的最新的值设置到vue实例上,因为vue实例响应化,响应化的setter函数会通知依赖进行更新操作。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值