Languages like C, have memory management primitives like malloc() and free().
JavaScript allocates values when things (objects, strings, numbers, etc.) are created and tries to automatically freed them when they are not used anymore. This process is also known as garbage collection.
Sometimes this “automatically done process” can be a source of confusion for some developers.
Memory lifecycle in JavaScript
The memory lifecycle is pretty much the same, regardless of the programming language.
- Allocate the memory you need
- Use it (read, write)
- Release the allocated memory when it is not needed anymore
Some Examples of Memory Allocation in JavaScript
var nNumber = 123;
// allocates memory for a numbervar sString = “dynamic";
// allocates memory for a stringvar oObject = { a: 1, b: null };
// allocates memory for an object and contained valuesvar aArray = [1, null, “adico"];
// (like object) allocates memory for the array and contained valuesfunction add(a){ return a + 2; }
// allocates a function (which is a callable object)- Function expressions also allocate an object
someElement.addEventListener('click', function(){ someElement.style.backgroundColor = ‘green'; }, true);
- Allocation via function calls
var date = new Date(); var el = document.createElement('div'); // allocates a DOM element
Garbage Collection Phase
Most of memory management issues come at this phase. The hardest task for any programming language is figuring out when a previously allocated memory is not needed anymore. High-level languages like Java have the concept of the garbage collector, that automatically runs and recollects spaces that are not in use anymore.
Garbage collection algorithms
-
Reference-counting garbage collection
- An object is said to reference another object if the former has access to the latter (either implicitly or explicitly).
- An object is considered garbage collectible if there are zero references pointing to the object.
Example:
var o = { // 2 objects are created. One is referenced by the other as one of its property. a: { // The other is referenced by virtue of being assigned to the 'o' variable. b:2 // Obviously, none can be garbage-collected } }; var o2 = o; // the 'o2' variable is the second thing that has a reference to the object o = 1; // now, the object that was originally in 'o' has a unique reference embodied by the 'o2' variable var oa = o2.a; // reference to 'a' property of the object. 2 references: one as a property, the other as the 'oa' variable o2 = “YOLO"; // The object 'o' has now zero references to it. // It can be garbage-collected. However what was its 'a' property is still referenced by the 'oa' variable, so it cannot be free'd oa = null; // it can be garbage collected.
-
Limitation: cycles
This algorithm has the limitation that if objects reference one another (and form a cycle), even though they may be “not needed anymore” they simply cannot garbage-collectible.
Internet Explorer 6, 7 are known to have a reference-counting garbage collector for DOM objects.
var div = document.createElement("div"); div.onclick = function(){ doSomething(); };
-
Mark-and-sweep algorithm
- This algorithm reduces the definition of “an object is not needed anymore” to “an object is unreachable”.
- This algorithm assumes the knowledge of a set of objects called roots (In JavaScript, the root is the global object).
- Periodically, the garbage collector will start from these roots and traverse down all reachable objects (that are referenced from these roots and their children) and collect all non-reachable objects
- As of 2012, all modern browsers ship a mark-and-sweep garbage collector.
- Cycles are not a problem anymore.
- In the previous example, once the div and its handler are made unreachable from the roots, they can both be garbage-collected despite referencing each other