vue源码学习之Object.defineProperty对象属性监听


Posted in Javascript onMay 30, 2018

本文介绍了vue源码学习之Object.defineProperty对象属性监听,分享给大家,具体如下:

参考版本 vue源码版本:0.11

相关

vue实现双向数据绑定的关键是 Object.defineProperty ,让我们先来看下这个函数。

在MDN上查看有关Object.defineProperty 的解释。

我们先从最简单的开始:

let a = {'b': 1};
Object.defineProperty(a, 'b', {
  enumerable: false,
  configurable: false,
  get: function(){
    console.log('b' + '被访问');
  },
  set: function(newVal){
    console.log('b' + '被修改,新' + 'b' + '=' + newVal);
  }
});

a.b = 2;  // b被修改,新b=2
a.b;    // b被访问

这样,我们就能监听对象了!但问题并不仅仅这么简单。。。

我们可能会有对象中属性的值还是对象这种嵌套情况,可以通过递归解决!

在vue源代码文件 srcobserveobserver.js 中

// 观察者构造函数
function Observer(data){
  this.data = data;
  this.walk(data);
}

let p = Observer.prototype;
p.walk = function(obj){
  let val;
  for(let key in obj){
    // 通过 hasOwnProperty 过滤掉一个对象本身拥有的属性 
    if(obj.hasOwnProperty(key)){
      val = obj[key];
      // 递归调用 循环所有对象出来
      if(typeof val === 'object'){
        new Observer(val);
      }
      this.convert(key, val);
    }
  }
};

p.convert = function(key, val){
  Object.defineProperty(this.data, key, {
    enumerable: false,
    configurable: false,
    get: function(){
      console.log(key + '被访问');
    },
    set: function(newVal){
      console.log(key + '被修改,新' + key + '=' + newVal);
      if(newVal === val) return ;
      val = newVal;
    }
  })
};

let data = {
  user: {
    name: 'zhangsan',
    age: 14
  },
  address: {
    city: 'beijing'
  }
}

let app = new Observer(data);
data.user.name;  // user被访问

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
iframe异步加载实现点击左边菜单加载右边内容实例讲解
Mar 04 Javascript
jquery删除数据记录时的弹出提示效果
May 06 Javascript
javascript实现的多个层切换效果通用函数实例
Jul 06 Javascript
基于javascript实现九九乘法表
Mar 27 Javascript
jquery实现全选和全不选功能效果的实现代码【推荐】
May 05 Javascript
Bootstrap Paginator分页插件与ajax相结合实现动态无刷新分页效果
May 27 Javascript
AngularJS基础 ng-hide 指令用法及示例代码
Aug 01 Javascript
使用vue-cli打包过程中的步骤以及问题的解决
May 08 Javascript
详解javascript 正则表达式之分组与前瞻匹配
May 30 Javascript
一文读懂ES7中的javascript修饰器
May 06 Javascript
微信小程序全局变量改变监听的实现方法
Jul 15 Javascript
Vue中正确使用Element-UI组件的方法实例
Oct 13 Javascript
Angular搜索场景中使用rxjs的操作符处理思路
May 30 #Javascript
微信小程序实现跑马灯效果完整代码(附效果图)
May 30 #Javascript
vue通过点击事件读取音频文件的方法
May 30 #Javascript
vue 表单输入格式化中文输入法异常问题
May 30 #Javascript
详解如何使用babel进行es6文件的编译
May 29 #Javascript
基于打包工具Webpack进行项目开发实例
May 29 #Javascript
JavaScript反射与依赖注入实例详解
May 29 #Javascript
You might like
收音机鉴频器对声音的影响和频偏分析
2021/03/02 无线电
php 分页函数multi() discuz
2009/06/21 PHP
php 验证码实例代码
2010/06/01 PHP
php若干单维数组遍历方法的比较
2011/09/20 PHP
php提示Failed to write session data错误的解决方法
2014/12/17 PHP
不常用但很实用的PHP预定义变量分析
2019/06/25 PHP
Code:loadScript( )加载js的功能函数
2007/02/02 Javascript
IE中radio 或checkbox的checked属性初始状态下不能选中显示问题
2009/07/25 Javascript
javascript 静态对象和构造函数的使用和公私问题
2010/03/02 Javascript
js 弹出框 替代浏览器的弹出框
2010/10/29 Javascript
javascript定义函数的方法
2010/12/06 Javascript
了解jQuery技巧来提高你的代码(个人觉得那个jquery的手册很不错)
2012/02/10 Javascript
纯js分页代码(简洁实用)
2013/11/05 Javascript
javascript事件函数中获得事件源的两种不错方法
2014/03/17 Javascript
javascript表单验证和Window详解
2014/12/11 Javascript
使用JavaScript开发IE浏览器本地插件实例
2015/02/18 Javascript
微信小程序教程系列之设置标题栏和导航栏(7)
2020/06/29 Javascript
JS实现table表格固定表头且表头随横向滚动而滚动
2017/10/26 Javascript
vue将时间戳转换成自定义时间格式的方法
2018/03/02 Javascript
vue+iview实现分页及查询功能
2020/11/17 Vue.js
简单介绍Python下自己编写web框架的一些要点
2015/04/29 Python
Python实现快速排序算法及去重的快速排序的简单示例
2016/06/26 Python
python 上下文管理器使用方法小结
2017/10/10 Python
Python给你的头像加上圣诞帽
2018/01/04 Python
python实现推箱子游戏
2020/03/25 Python
python中while和for的区别总结
2019/06/28 Python
Python with关键字,上下文管理器,@contextmanager文件操作示例
2019/10/17 Python
Python3 Click模块的使用方法详解
2020/02/12 Python
Python连接Mysql进行增删改查的示例代码
2020/08/03 Python
Python如何爬取b站热门视频并导入Excel
2020/08/10 Python
Ajax实现页面无刷新留言效果
2021/03/24 Javascript
摄影实习自我鉴定
2013/09/20 职场文书
教师实习期自我鉴定
2013/10/06 职场文书
2015年出纳个人工作总结
2015/04/02 职场文书
2015教师个人年度工作总结
2015/10/23 职场文书
电力安全学习心得体会
2016/01/18 职场文书