事件侦听器会阻止垃圾收集外部函数作用域中引用的对象吗?

问题描述 投票:0回答:1

假设我有以下代码:

(function () {

    const largeObject = provideSomeLargeObject();
    const largeStaticListOfElements = document.querySelectorAll('span');
    const someElementThatWillBeRemoved = document.getElementById('i-will-be-removed');

    const elms = document.getElementsByClassName('click-me');

    for (let i = 0; i < elms.length; ++i) {

        const anotherLargeObject = provideAnotherLargeObject();

        elms[i].addEventListener('click', function (e) {
            // callback just uses i, which contains a literal value
            e.preventDefault();
            console.log(i);
        });
    }

    // largeObject, largeStaticListOfElements, someElementThatWillBeRemoved, and anotherLargeObject
    // are no longer used in this code. Should they be set to null to allow GC them?

})();

事件监听器创建函数作用域,执行上述代码后,事件监听器仍然存在,因此外部函数作用域被保留,以便事件处理程序可以使用它们包含的变量。

但是,事件处理程序仅使用外部作用域中的一些文字值,但在这些作用域中还有其他变量,不再使用。

  • 事件侦听器是否会阻止对这些变量引用的对象进行垃圾收集,因此我必须在代码末尾手动将 null 分配给变量,
  • 或者 JavaScript 引擎是否足够聪明,能够检测到事件处理程序从不使用变量,因此即使变量驻留在仍然存在的函数作用域中,引用的对象也可以被 GC?
javascript memory memory-leaks reference garbage-collection
1个回答
0
投票

重要的不是事件侦听器,而是如何声明整个过程中的每个标识符。

因此,如果您非常担心垃圾收集器完成其工作(您应该如此),您可能希望避免将所有内容声明为常量,这是不必要的!

GOOD常量声明示例...

const DaysOfWeek=['Sunday','Monday','Tuesday','Wednesday','Thursday','Friday','Saturday'];

const MyName='John Citizen';

const CompanyHome='https:/ourcompany.com/';

BAD常量声明的示例...

const largeObject = provideSomeLargeObject();

const largeStaticListOfElements = document.querySelectorAll('span');

const someElementThatWillBeRemoved = document.getElementById('i-will-be-removed');

const elms = document.getElementsByClassName('click-me');

你明白了......

© www.soinside.com 2019 - 2024. All rights reserved.