在Javascript中管理内存变量的最佳方法是什么?

时间:2013-03-12 10:22:17

标签: javascript memory-management memory-leaks

我正在通过Javascript构建一个基于浏览器的Web应用程序。

当我需要一个位于单独文件中的模块时,我不知道这三种方法中哪一种最适合javascript引擎占用的内存:

构思1 在extend方法中分配变量

function (ContactCollection , ItemCollection, ContactListView) {
    var ContactExample = function (inst) {
         // Wild examples of possible uses :

         this.collections.contact.each(function(model) {
             // do something with each model
         });

         this.collections.item.on('reset', this.resetItems, this);

         this.$el.remove().append(this.view.render().el);
    };

    jQuery.extend(true, ContactExample.prototype, {
        'collections': {
            'contact': ContactCollection,
            'item': ItemCollection
        },
        'view': ContactListView,
        '$el': jQuery('#somediv'),
    }, ContactExample);

    return new ContactExample();
};

构思2 在实例化方法中分配变量

function (ContactCollection , ItemCollection, ContactListView) {
    var ContactExample = function (inst) {
         // Wild examples of possible uses :

         inst.collections.contact.each(function(model) {
             // do something with each model
         });

         inst.collections.item.on('reset', this.resetItems, this);

         inst.$el.remove().append(this.view.render().el);
    }

    jQuery.extend(true, ContactExample.prototype, {
        '$el': jQuery('#somediv')
    }, ContactExample);

    return new ContactExample({
        'collections': {
            'contact': ContactCollection,
            'item': ItemCollection
        },
        'view': ContactListView
    });
};

构思3 只需在代码中使用它们,因为它们已在函数范围内引用

function (ContactCollection , ItemCollection, ContactListView) {
    var ContactExample = function (inst) {
         // Wild examples of possible uses :

         ContactCollection.each(function(model) {
             // do something with each model
         });

         ItemCollection.on('reset', this.resetItems, this);

         this.$el.remove().append(ContactListView.render().el);
        }
    });

    jQuery.extend(true, ContactExample.prototype, {
        '$el': jQuery('#somediv')
    }, ContactExample);

    return new ContactExample();
});

在javascript内存引擎中处理变量的最佳方法是什么(以及为什么)。

感谢您的回答

3 个答案:

答案 0 :(得分:1)

三个选项的最低内存使用率是使用上下文变量(想法#3),因为它消除了重复。另外两个将值复制到在该函数内创建的第二个对象。这是背景:

JavaScript中的所有内容都是一个对象,对象在内部只是将字符串键与其实际值的引用相关联的哈希映射。这包括普通的局部变量;在内部,它们是不可见上下文对象的属性,可以由该函数及其内部定义的任何函数访问。直接使用$ .extend vs assigning属性没有区别,因为extend函数只是围绕for循环的语法糖,它将属性从一个对象复制到另一个对象。

由于函数的上下文(局部变量)对象被保留以供其内部定义的所有函数使用,因此选项的最低内存使用量将是不将其复制到新内部对象的内存使用量。但差别很小。

如果你真的想把你的内存使用量降到最小的水平并编写更容易维护的代码,我建议摆脱花哨的(和难以调试的)上下文包装并将其编码为旧式JavaScript OOP方式:使用在顶层或在首次加载页面时仅运行一次的单个包装函数内定义的普通构造函数。这摆脱了重复的上下文。使用'new'关键字调用它,并将数据作为您分配给'this'的参数传入。在构造函数中进行初始化,仅此而已。

将所有方法函数放在其原型上,然后将其用作普通的,简洁的JavaScript对象。

https://developer.mozilla.org/en-US/docs/JavaScript/Introduction_to_Object-Oriented_JavaScript

答案 1 :(得分:0)

你为什么要使用$ .extend?只需创建一个实例并分配属性:

var c = new ContactExample();
c.$el = $('#somediv');

内存不会成为问题 - 而是专注于可能导致问题的DOM元素(#somediv)的引用。

答案 2 :(得分:0)

  • 常数

    • 如果您不需要在函数范围之外使用它们,请使用普通变量。

    • 如果您需要在函数范围之外使用它们,请将它们放在构造函数上。

  • 实例变量(随每个实例而变化)

    • 对于您知道每个实例具有不同值的属性,请在构造函数中使用正确的类型声明它们,以便可以将它们优化为与构造函数关联的静态类型。

    • 对于所有对象(如方法)共享的属性,请使用原型。

    • 对于更有可能保留其默认值的属性,如果您想要访问速度,则应在构造函数中声明它们,但如果要使用更少的内存,则应将默认值放在构造函数,如果它与默认值不同,则只向对象添加属性。