Note that there are some explanatory texts on larger screens.

plurals
  1. POJavascript closure : Memory Leak
    text
    copied!<p>I have a memory leak I don't understand. I programmed a mechanism to handle event with semi-automatically unbinding which should allow me to clean up memory easily. But in one case, the clean up doesn't happen (I use chrome's "profile (memory heap)" to check for instances of "EventHandler" left). I really don't get why it happen. There's something weird with the closure...</p> <p><a href="http://serge.snakeman.be/Demo/test.html" rel="nofollow">see it in action with chrome</a></p> <pre><code>function Bind(obj, f) { return function() { return f.apply(obj, arguments); } } function EventHandler() { this.listeners = new Object(); var _listenerID = 0; this.addListener = function(e, obj, listener, specialDisplay) { if (typeof(listener) === "function") { var listenerID = ++_listenerID; console.log("Events (" + (++EventHandler.All) + ", " + listenerID + ") ++" + e); if (!this.listeners.hasOwnProperty(e)) { this.listeners[e] = new Object(); } this.listeners[e][listenerID] = listener; if (obj != null &amp;&amp; typeof(obj.removeListener) == "function") { var deleteListenerID = obj.addListener("Delete", null, Bind(this, function() { this.removeListener(e, listenerID); obj.removeListener("Delete", deleteListenerID); })); } return listenerID; } return null; } this.fire = function(e, obj) { if (this.listeners.hasOwnProperty(e)) { for(var i in this.listeners[e]) { this.listeners[e][i](obj); } } } this.removeListener = function(e, listenerID) { if (this.listeners.hasOwnProperty(e) &amp;&amp; this.listeners[e].hasOwnProperty(listenerID)) { delete this.listeners[e][listenerID]; console.log("Events (" + (--EventHandler.All) + ", " + listenerID + ") --" + e); } } } EventHandler.All = 0; function Loader() { } Loader.files = new Object(); Loader.LoadImage = function(src, f) { if (!Loader.files.hasOwnProperty(src)) { var handler = new EventHandler(); console.log("Loading.... (" + src + ")"); Loader.files[src] = function(fnct) { handler.addListener("ImageLoaded", handler, function(img) { fnct(img); }); } handler.addListener("ImageLoaded", handler, function() { Loader.files[src] = function(fnct) { fnct(img); } }); var img = new Image(); $(img).load(function() { console.log("Loaded.... (" + src + ")"); handler.fire("ImageLoaded", img); handler.fire("Delete"); $(img).unbind('load'); }); img.src = src; } Loader.files[src](f); } Loader.LoadImage("http://serge.snakeman.be/Demo/house.jpg", function() { alert("ok"); }); </code></pre>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload