【问题标题】:Get all instances of class in Javascript获取 Javascript 中类的所有实例
【发布时间】:2013-10-31 19:55:33
【问题描述】:

我以为已经有答案了,但我似乎找不到答案.. 如何在 Javascript 中对此类的所有实例运行特定的类方法?

这必须在我不知道实例名称的情况下完成。 我想我可以在我的类中使用某种静态变量来存储所有实例,但这似乎在 JS 中不存在

那么如何在我的类的所有现有实例上调用我的方法? 注意:只是为了澄清:我不是在谈论 CSS 类,我是在谈论对象。

编辑:在 Javascript 中,我的意思是在函数上创建一个新对象:

function something()
{
}

var instance = new something();

【问题讨论】:

  • 您要求创建内存泄漏。
  • document.getElementsByClassName()? jQuery class selector?我在这里错过了什么吗?
  • @SLaks 为什么?我不明白。
  • 啊,我明白了。 (JavaScript 中没有类,所以术语把我吓坏了。)
  • 一般来说,人们只需要知道一个(提示!)collection 所述对象。使用这个想法将对象分组到适当的(分层的)集合中,并以此设计 API。例如,一张地图可能有很多点,但通常并不关心创建的每个点;相反,只有属于特定地图的点 - 通过位于适当的点collection - 特定地图是感兴趣的。

标签: javascript class object


【解决方案1】:

在 Chrome 62+ 中,您可以使用 queryObjects from the console API - 它在本机 JavaScript 代码中不起作用,但在控制台中,因此它非常适合调试

class TestClass {};
const x = new TestClass();
const y = new TestClass();
const z = new TestClass();
queryObjects(TestClass)

【讨论】:

    【解决方案2】:

    现在可以在类中使用关键字“静态”(但请检查支持),...

    https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes/static

    class Point{
        constructor(x, y){
            this.x = x;
            this.y = y;
            Point.all.push(this);
        }
        destroy(){
            let i = Point.all.indexOf(this);
            Point.all.splice(i, 1);
        }
        static all = [];
    }
    
    var p1 = new Point(1, 2);
    var p2 = new Point(54, 33);
    var p3 = new Point(297, 994);
    
    console.log(JSON.stringify(Point.all)); //[{"x":1,"y":2},{"x":54,"y":33},{"x":297,"y":994}]
    
    p2.destroy();
    console.log(JSON.stringify(Point.all)); //[{"x":1,"y":2},{"x":297,"y":994}]

    【讨论】:

      【解决方案3】:

      很抱歉这么晚才回复,但我发现自己正在努力实现这一点,我认为这可能是一个更简单的答案。

      假设你想要 MyClass 类的所有实例,只获取在顶层窗口级别创建的实例(不包括在闭包内创建的实例):

      for (var member in window)
      {
          if (window[member] instanceof MyClass)
              console.info(member + " is instance of MyClass");
      }
      

      【讨论】:

        【解决方案4】:

        您必须提供自定义实现。

        我会做这样的事情:

        function Class() {
            Class.instances.push(this);
        };
        Class.prototype.destroy = function () {
            var i = 0;
            while (Class.instances[i] !== this) { i++; }
            Class.instances.splice(i, 1);
        };
        Class.instances = [];
        
        var c = new Class();
        Class.instances.length; // 1
        c.destroy();
        Class.instances.length; // 0
        

        或者像这样:

        function Class() {};
        Class.instances = [];
        Class.create = function () {
            var inst = new this();
            this.instances.push(inst);
            return inst;
        };
        Class.destroy = function (inst) {
            var i = 0;
            while (Class.instances[i] !== inst) { i++; }
            Class.instances.splice(i, 1);
        };
        
        var c = Class.create();
        Class.instances.length; // 1
        Class.destroy(c);
        Class.instances.length; // 0
        

        然后你可以像这样遍历所有实例:

        Class.each = function (fn) {
            var i = 0, 
                l = this.instances.length;
            for (; i < l; i++) {
                if (fn(this.instances[i], i) === false) { break; }
            }
        };
        
        Class.each(function (instance, i) {
            // do something with this instance
            // return false to break the loop
        });
        

        【讨论】:

          【解决方案5】:

          您需要自己存储一个实例列表:

          function someClass(param) {
          
            // add to all
            if (this.constructor.all === undefined) {
              this.constructor.all = [this];
            } else {
              this.constructor.all.push(this);
            }
          
            // set param
            this.logParam = function() { console.log(param); };
          }
          
          var instance1 = new someClass(1);
          var instance2 = new someClass(2);
          
          for (var i = 0; i < someClass.all.length; i++) {
            someClass.all[i].logParam();
          }
          

          如果内存泄漏是一个问题,那么您可以创建一个方法来在完成实例后删除它们:

          function someClass(param) {
          
            ...
          
            this.destroy = function() {
              var all = this.constructor.all;
              if (all.indexOf(this) !== -1) {
                all.splice(all.indexOf(this), 1);
              }
              delete this;
            }
          }
          

          【讨论】:

            【解决方案6】:

            您可以创建一个静态数组并将其存储在您的构造函数中:

            MyClass.allInstances = [];
            MyClass.allInstances.push(this);
            

            但是,您需要一些方法来确定何时从该数组中删除实例,否则您会泄漏内存。

            【讨论】:

            • 好的,现在我明白你为什么要谈论内存泄漏了。好吧,我将实现某种析构函数
            • 你不能把'MyClass.allInstances = []'放在构造函数中,它每次都会创建一个空数组:(
            • @DamjanPavlica:当然;这些需要在不同的地方。
            猜你喜欢
            • 2021-08-23
            • 2017-06-09
            • 1970-01-01
            • 2019-01-29
            • 1970-01-01
            • 2012-04-26
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多