观察者模式一般包含发布者(Publisher)和订阅者(Subscriber)两种角色;顾名思义发布者负责发布消息,订阅者通过订阅消息响应动作了。
回到Vue中,在Vue源码core/oberver目录下分析代码可以知道有三个类分别是Oberver,Watcher和Dep

function Observer(data) {//在Observer实例上,暂存datathis.data = data;this.walk(data);
}Observer.prototype = {walk: function(data) {var me = this;//对data里所有的属性名进行遍历。Object.keys(data).forEach(function(key) {me.convert(key, data[key]);});},convert: function(key, val) {//为每个属性增加响应式。this.defineReactive(this.data, key, val);},defineReactive: function(data, key, val) {//为data中所有层次的属性,都创建一个dep实例。var dep = new Dep();//递归遍历data中,所有层次的属性。var childObj = observe(val);//为原有属性新增get和set方法(数据劫持)Object.defineProperty(data, key, {enumerable: true, // 可枚举configurable: false, // 不能再defineget: function() {//判断当前Dep.target的watcher是否存在if (Dep.target) {//当模版初始化的时候会赋值watcher实例到target上//调用dep的depend方法dep.depend();}return val;},set: function(newVal) {if (newVal === val) {return;}val = newVal;// 新的值是object的话,进行监听。childObj = observe(newVal);// 通知订阅者。dep.notify();}});}
};
function observe(value, vm) {//判断value是否存在或者value的数据类型是否为object(递归的终止条件)。if (!value || typeof value !== 'object') {return;}return new Observer(value);
};
var uid = 0;
function Dep() {//没创建一个dep都会给这个dep增加一个独立的标识。this.id = uid++;this.subs = []; //watcher
}Dep.prototype = {addSub: function(sub) {this.subs.push(sub);},//调用watcher实例的addDep方法。depend: function() {//Dep.target此时是watcher的实例//this此时是当前dep的实例Dep.target.addDep(this);},removeSub: function(sub) {var index = this.subs.indexOf(sub);if (index != -1) {this.subs.splice(index, 1);}},//通知所有的watchernotify: function() {// beforeUpdate//遍历subs中所有的watcher的实例this.subs.forEach(function(sub) {// 每一个watcher的实例调用update方法sub.update();});// updated}
};
Dep.target = null;

Vue源码分析 - observer.js相关推荐

  1. Vue源码分析 - mvvm.js

    什么是MVVM MVVM是Model-View-ViewModel的简写.即模型-视图-视图模型. 模型指的是后端传递的数据. 视图指的是所看到的页面. 视图模型是mvvm模式的核心,它是连接view ...

  2. Vue源码分析 - watcher.js

    function Watcher(vm, exp, cb) {//在watcher的实例上保存回调函数this.cb = cb; //用于更新界面的回调函数this.vm = vm; //MVVM的实 ...

  3. Vue源码分析 - compile.js

    function Compile(el, vm) {this.$vm = vm; //this是Compile的实例 //$vm 是MVVM的实例 (vm)// el == "#app&qu ...

  4. [Vue源码分析] 模板的编译

    最近小组有个关于vue源码分析的分享会,提前准备一下- 前言: Vue有两个版本:Runtime + Compiler . Runtime only ,前者是包含编译代码的版本,后者不包含编译代码,编 ...

  5. [Vue源码分析]自定义事件原理及事件总线的实现

    最近小组有个关于vue源码分析的分享会,提前准备一下- 前言: 我们都知道Vue中父组件可以通过 props 向下传数据给子组件:子组件可以通过向$emit触发一个事件,在父组件中执行回调函数,从而实 ...

  6. [Vue源码分析] v-model实现原理

    最近小组有个关于vue源码分析的分享会,提前准备一下- 前言: 我们都知道使用v-model可以实现数据的双向绑定,及实现数据的变化驱动dom的更新,dom的更新影响数据的变化.那么v-model是怎 ...

  7. vue源码分析系列二:$mount()和new Watcher()的执行过程

    续vue源码分析系列一:new Vue的初始化过程 在initMixin()里面调用了$mount() if (vm.$options.el) {vm.$mount(vm.$options.el);/ ...

  8. Vue源码分析——第三章

    Vue源码分析--第一章 Vue源码分析--第二章 // only used in dev mode//检测 val必需是数字function checkDuration(val, name, vno ...

  9. Vue源码分析--Vue.component

    Vue源码分析–Vue.component 我将非 Vue.component 的部分去掉了 export function initAssetRegisters (Vue: GlobalAPI) { ...

最新文章

  1. 第八课.EM算法的合理性与算法推导
  2. 在AI领域每月投资一次,全面解析腾讯的人工智能奇招
  3. python管理系统项目首选公司_Python 项目的部署,目前互联网公司有哪些成熟的方案?...
  4. GRPC golang版源码分析之客户端(二)
  5. tensorflow计算图_简单谈谈Tensorflow的运行机制
  6. 购物场景的对话流程如何实现?
  7. C++ Opengl 绘制字体源码
  8. Springboot注册Filter
  9. Numpy基础(part2)--ndarray数组
  10. [leetcode ]429. N-ary Tree Level Order Traversale (easy)
  11. 中山大学Delphi视频教程 共51课
  12. SQL Server Alwayson概念总结
  13. (转)测试用例的设计方法(全)之三 判定表、正交实验
  14. hadoop入门-centos7.2安装hadoop2.8
  15. RFID防盗安全门,自助借还书机,让图书馆发展进入新的里程碑
  16. 微信公众号 多台服务器,在多台 Linux 服务器上搭建 Pulsar 集群
  17. java 骑士飞行棋_C#实现骑士飞行棋
  18. win10装的AutoCAD 2012版,右上角最小化不显示的解决办法
  19. HT1621B驱动液晶LCD连接及程序
  20. 仓库管理系统软件哪个好

热门文章

  1. [SGU223]Little Kings(状压DP)
  2. bzoj 3670 [NOI2014]动物园
  3. CODE[VS] 1098 均分纸牌 ( 2002年NOIP全国联赛提高组)
  4. 《人人都可以创业》连载1:创业很简单,从心开始
  5. Delphi在代码编辑栏按回车无法换行
  6. Bailian2742 Number of letters【入门】
  7. CCF201803-3 URL映射(100分)【文本处理+暴力】
  8. 九章算术卷第三 衰分
  9. 极简算法 —— 判断两字符串是否为相同字母的不同顺序组成
  10. 工具的使用 —— PyCharm/IDEA 常用快捷键