Memory mechanics with scope

2019-07-18 08:40发布

问题:

If I do something like

// global scope
function stuff() {
    // local scope
    var a = new SomeHugeMemoryHog();
}

// a doesn't exist down here, but what happened to the memory from the "stuff" scope?

Will I create a memory leak if I don't set a = null at the end of the stuff scope? Or should I not worry about it? I'm asking this question with emphasis on creating DOM objects (such as a canvas) inside the scope of functions (which I don't use later at any time). I'm only using the canvas to grab vector dimensions.

回答1:

As others have pointed out that since there is no reference to a outside the function the garbage collector will collect it, most likely on the next collection.

Some things you need to watch out for, however, is indirect capture. A common place this happens is in event handlers through closure capture. For example,

function stuff() {
    var a = new SomeLargeObject();
    $("#somediv").click(function () { /* something */ });
}

Even if the nested function doesn't use a. a might be kept alive because the activation record of stuff is still alive. Also, DOM objects might be collected differently than normal JavaScript objects which might cause them to be susceptible circular referneces causing collection problems. This most problematic in older browsers and since you reference using a canvas browsers that support canvas tend to be more modern and correctly handle circular references as well as allowing local variables not captured by a closure to collect.



回答2:

No, it should get garbage collected once there are no more references to it.



回答3:

You shouldn't worry about it. a will be a local global within the stuff() function (and visible to any code that runs "lower", but will not visible outside of the stuff() call.

e.g.

<script>
// a does not exist here

function stuff() {
   // no a here
   var a = new SomeHugeMemoryHog(); // a will be set once SomeHugeMemoryHog is created and the constructor returns
   // a exists here
}

// no a here either

stuff(); // a exists while stuff is running

// a has gone out of scope and will be cleaned up.

</script>


回答4:

The only case I can see a possible memory leak is when your function is actually used as a constructor. i.e.

var someObj = new stuff();

Otherwise, the variable a will get garbage collected.