Object.observe简介

Object.observe 是一个提供数据监视的API,在chrome中已经可以使用。是 ECMAScript 7 的一个提案规范,官方建议的是“谨慎使用”级别,但是个人认为这个API非常有用,例如可以对现在流行的MVVM框架作一些简化和优化。虽然标准还没定,但是标准往往是滞后于实现的,只要是有用的东西,肯定会有越来越多的人去使用,越来越多的引擎会支持,最终促使标准的生成。

可以做什么

从observe字面意思就可以知道,这玩意儿就是用来做观察者模式之类的东东。

简单地说,就是观察一个对象的变化,在被观察者变化时作出一些回调。

实际应用中,可以优化数据模型(model)和网页试图(view)的双向绑定。

语法

语法很简单:

Object.observe(obj, callback)
obj

obj就是你要监听的数据模型(例如一个ajax接口对应的数据)

callback

callback就是数据模型变化后触发的回调(例如网页视图的变化)

callback函数的参数形式
  • name: 被修改的属性名称
  • object: 修改后该对象的值
  • type: 表示对该对象做了何种类型的修改,可能的值为"add", "update", "delete", "reconfigure"
  • oldValue: 对象修改前的值。该值只在"update"与"delete"有效

实例:

感兴趣可以跑一下下面简单的代码,你就知道各个参数的作用了

<!doctype html>
<html>
    <head>
        <meta charset="utf-8">
    </head>
    <body>
        <script>
            var obj = {};
            Object.observe(obj, function (changes) {
                changes.forEach(function (change) {
                    console.log('变化的属性:  ' + change.name);
                    console.log('变化的类型?: ' + change.type);
                    console.log('旧值:  ' + change.oldValue);
                    console.log('新值:  ' + change.object[change.name]);
                });
            });
        </script>
    </body>
</html>

实现MVVM

当然这里不是要取代MVVM框架,只是想通过Object.observe来实现一些性能上的优化。

Angular中有一个叫“脏值检查”的东西,大概的原理就是只要任何时候数据发生了变化,这个库都会通过一个digest或者change cycle去检查变化是否发生了。在Angular中,一个digest循环意味着所有所有被监视的表达式都会被循环一遍以便查看其中是否有变化发生。

用以下代码,大大优化了脏值检查

<!doctype html>
<html>
    <head>
        <meta charset="utf-8">
        <title>real MVVM</title>
    </head>
    <body>
        <form id="person">
            <input type="text" name="name" placeholder="名字">
            <input type="text" name="age" placeholder="年龄">
        </form>

        <script>
            var view = document.getElementById('person');
            var infomation = {};

            function bind(model, view) {
                Object.observe(model, function (changes) {
                    changes.forEach(function (change) {
                        var property = change.name;
                        document.getElementsByName(property)[0].value = change.object[property];
                    });
                });

                Array.prototype.slice.call(view.getElementsByTagName('input')).forEach(function (input) {
                    input.addEventListener('input', function (e) {
                        var input = e.target;
                        if (input.tagName.toLowerCase() !== 'input') {
                            return;
                        }
                        var property = input.getAttribute('name');
                        model[property] = input.value;
                    });
                });
            }

            bind(infomation, view);
        </script>
    </body>
</html>

脏值检查在任何数据可能发生变化的时候都必须要运行。这很明显并不是一个非常鲁棒的方法,并且任何实现脏值检查的途径都是有缺陷的(例如,在轮询中进行检查可能会造成视觉上的假象以及涉及到代码的紊乱情况)。脏值检查也需要注册一个全局的观察者,这很可能会造成内存泄漏,而Object.observe()会避免这一点。

参考

http://www.html5rocks.com/en/tutorials/es7/observe/

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏腾讯IVWEB团队的专栏

Object.observe 简介

Object.observe 是一个提供数据监视的API,在chrome中已经可以使用。是 ECMAScript 7 的一个提案规范,官方建议的是“谨慎使用”级...

2600
来自专栏XAI

那些年Struts 1.X 而今我还是不会

struts1是WEB程序MVC分层架构中的C,属于控制层,主要进行处理用户的请求,基于请求驱动。 获取用户的请求地址并将表单中的数据封装到Form 对象后交给...

1937
来自专栏程序员互动联盟

【答疑释惑第三十四讲】Web js 常见用法

疑惑一 一、js中怎么实现hashcode值? 在java中有一种方法,就是可以获取字符串的对应的hashcode值,返回对应的整数值; 这个方法对于一些写在数...

3015
来自专栏向治洪

android应用资源预编译,编译和打包全解析

我们知道,在一个APK文件中,除了有代码文件之外,还有很多资源文件。这些资源文件是通过Android资源打包工具aapt(Android Asset P...

38110
来自专栏前端小叙

koa2使用注意点总结

get请求,ajax传入参数 获取的时候为ctx.request.query.参数名

762
来自专栏木宛城主

Unity应用架构设计(6)——设计动态数据集合ObservableList

什么是 『动态数据集合』 ?简而言之,就是当集合添加、删除项目或者重置时,能提供一种通知机制,告诉UI动态更新界面。有经验的程序员脑海里迸出的第一个词就是 O...

1647
来自专栏WeaponZhi

MVVM 面向接口型框架封装和单元测试

大家好,今天给大家带来一个我自己开发改造的 MVVM 封装框架。代码不难,但我更想说一些我在开发这样一个架构过程中的想法和思路,我们不仅要善于作一个搬运工,更要...

3876
来自专栏python学习路

一、代码风格 1、假定你的代码需要维护2、保持一致性3、考虑对象在程序中存在的方式,尤其是那些带有数据的对象4、不要做重复工作5、让注释讲故事6、奥卡姆剃刀原则1、简洁的规则2、文档字符串3、空行4、

刚开始学的时候就要注意编码规范了,所以整理了一下,以便养成一个编码好习惯。不然以后真的不好改。 代码被读的次数远大于被写的次数。 作为一名程序员(使用任何语言)...

2275
来自专栏宋凯伦的技术小栈

【从业余项目中学习2】C# 实现调用Matlab函数(Visual Studio:2008, Matlab:R2009a)

  最近正在给客户做的个人项目,要求实现C#与Matlab之间的调用,即C# winform界面收集用户输入的参数,将参数传递给Matlab的算法计算,Matl...

2657
来自专栏LinXunFeng的专栏

iOS - Swift 面向协议编程(一)

1435

扫码关注云+社区