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 相关文章推荐
利用JS重写Cognos右键菜单的实现代码
Apr 11 Javascript
jquery 扑捉回车键事件代码
Apr 24 Javascript
javascript判断是手机还是电脑访问网页的简单实例分享
Jun 03 Javascript
jquery计算鼠标和指定元素之间距离的方法
Jun 26 Javascript
WordPress中利用AJAX技术进行评论提交的实现示例
Jan 12 Javascript
使用Promise解决多层异步调用的简单学习心得
May 17 Javascript
jQuery Mobile和HTML5开发App推广注册页
Nov 07 Javascript
JS路由跳转的简单实现代码
Sep 21 Javascript
iview table render集成switch开关的实例
Mar 14 Javascript
微信小程序开发的基本流程步骤
Jan 31 Javascript
Node.js动手撸一个静态资源服务器的方法
Mar 09 Javascript
vue项目中引入vue-datepicker插件的详解
May 14 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
怎样在php中使用PDF文档功能
2006/10/09 PHP
php自动获取字符串编码函数mb_detect_encoding
2011/05/31 PHP
PHP5下$_SERVER变量不再受magic_quotes_gpc保护的弥补方法
2012/10/31 PHP
PHP flock 文件锁详细介绍
2012/12/29 PHP
php对数组排序代码分享
2014/02/24 PHP
PHP中overload与override的区别
2017/02/13 PHP
非常好的js代码
2006/06/27 Javascript
javaScript对象和属性的创建方法
2007/01/15 Javascript
Jquery 学习笔记(一)
2009/10/13 Javascript
js简单实现让文本框内容逐个字的显示出来
2013/10/22 Javascript
JQuery实现倒计时按钮具体方法
2013/11/14 Javascript
Node.js实现批量去除BOM文件头
2014/12/20 Javascript
jQuery简单实现禁用右键菜单
2015/03/10 Javascript
js实现点击按钮后给Div图层设置随机背景颜色的方法
2015/05/06 Javascript
jquery validate表单验证的基本用法入门
2016/01/18 Javascript
AngularJS定时器的使用与移除操作方法【interval与timeout】
2016/12/14 Javascript
JavaScript中值类型和引用类型的区别
2017/02/23 Javascript
简述Angular 5 快速入门
2017/11/04 Javascript
vue+导航锚点联动-滚动监听和点击平滑滚动跳转实例
2019/11/13 Javascript
[01:08]DOTA2次级职业联赛 - Wings 战队宣传片
2014/12/01 DOTA
python 装饰器功能以及函数参数使用介绍
2012/01/27 Python
Python3几个常见问题的处理方法
2019/02/26 Python
tensorflow常用函数API介绍
2020/04/19 Python
IDLE下Python文件编辑和运行操作
2020/04/25 Python
Python实现七个基本算法的实例代码
2020/10/08 Python
基于HTML5的WebGL实现json和echarts图表展现在同一个界面
2017/10/26 HTML / CSS
萌新HTML5 入门指南(二)
2020/11/09 HTML / CSS
销售人员求职信
2014/07/22 职场文书
2014年重阳节老干部座谈会局领导发言稿
2014/09/25 职场文书
群众路线个人剖析材料
2014/10/07 职场文书
交警作风整顿剖析材料
2014/10/11 职场文书
六一晚会主持词开场白
2015/05/28 职场文书
高中班主任工作总结(范文)
2019/08/20 职场文书
Redis中一个String类型引发的惨案
2021/07/25 Redis
Spring Bean是如何初始化的详解
2022/03/22 Java/Android
Vue router配置与使用分析讲解
2022/12/24 Vue.js