2

如何检测对象的属性是否在 Javascript 中发生了变化?我特别希望在对象的属性数量发生变化时调用一个函数(无论它是获得还是丢失属性)。我想避免使用方法并设置和更改对象的属性,因为那样会很快变得相当笨拙,而且setInterval显然不是一种选择。那么,这可能吗?


编辑:我正在专门寻找一种方法来通过length类似于 Array 对象上的属性来获取对象属性的长度。我假设每当添加或删除索引时他们都会更改长度,但显然情况并非如此。Javascript 的原始设计者是如何做到这一点的?

4

3 回答 3

2

好吧,实现它的常用方法是使用 getter 和 setter 类型的函数来完成它,类似于骨干如何处理它的模型。您通过函数修改数据,然后函数在执行您想要执行的操作之前执行其他处理(如执行侦听器、检查属性等)。

function ListenableObject(data){

    var that = this;
    this.data = data;
    this.listeners = [];

    this.edit = function(newvalues){
        //modify data
        //execute listeners
    }

    this.addListener = function(callback){
        that.listeners.push(callback);
    }
}

var mydata = new ListenableObject({'foo':'bar'});

mydata.addListener(function(){...callback...});

mydata.edit(somedata);
于 2012-05-14T13:42:35.787 回答
1

根据您的要求,简短的回答是不可能做您想做的事情。至少,现在还没有。您可以使用一些技术来获得相同的功能,而对代码的影响最小。这是我个人最喜欢的一个——在 SO 的某个地方发现的——如果我能找到,我会链接。

function myObj(){

   var _this = this;

   // onUpdate callbacks
   this.onBeforeUpdate = [];
   this.onAfterUpdate  = [];

   this.UpdateProperty = function( prop, value ){

      // execute onBeforeUpdate callbacks...  
      for ( var i = 0; i < _this.onBeforeUpdate.length; i++ )
         _this.onBeforeUpdate[i]();

      _this[prop] = value;

      // execute onAfterUpdate callbacks...
      for ( var i = 0; i < _this.onAfterUpdate.length; i++ )
         _this.onAfterUpdate[i]();
   };

}

当然,通过大量使用原型分配,可以使这个示例表现得更好,但您可以看到其意图。

于 2012-05-14T14:08:31.557 回答
1

因此,总结一下我通过评论所说的一切:ES6 将提供代理,这些代理应该为“新属性”或“属性已删除”等事件启用处理程序。(不过,我并没有对此进行过多研究。)不幸的是,代理成为跨浏览器还需要数年时间。

至于length对象的属性,你可以为它定义一个getter函数,但这会在IE8中中断,因为IE只在IE9中实现了getter。所以,这给你留下了一个length()方法。所以:

function objectLength () {
    return Object.keys( this ).length;
}

然后,确保您的对象具有此功能(作为自己的属性或继承的属性):

yourObj.length = objectLength;

或者

YourConstructor.prototype.length = objectLength;
于 2012-05-14T14:34:00.767 回答