假设我有一个动态加载页面的页面。当每个页面加载到 DOM 中时,就会添加该页面中元素的事件。
如果用户加载另一个页面,先前加载的元素将从 DOM 中删除。当然,由于元素本身不再存在,映射到这些元素的任何事件都将停止运行。
然而,它们也被删除了吗?或者它们是否存在于用户的记忆中,占用空间?
后续:
是否有这样定义的函数:
var event = $('foobar').addEvent('click', function() {
alert(1);
});
可以使用 event = null
轻松删除事件(或者我是这么假设的!)...
但是如果事件没有保存到局部变量中怎么办?
$('foobar').addEvent('click', function() {
alert(1);
});
谢谢!
Let's say I have a page that loads pages dynamically. As each page loads into the DOM, events for the elements in that page are added.
If the user loads another page, the elements loaded previously will be removed from the DOM. Naturally, because the elements themselves no longer exist, any events mapped to those elements cease to function.
However, are they also removed? Or are they sitting in the user's memory, taking up space?
Follow-up:
Were a function defined as such:
var event = $('foobar').addEvent('click', function() {
alert(1);
});
One could easily remove the event with event = null
(or so I'd assume!)...
but what if the event were not saved to a local variable?
$('foobar').addEvent('click', function() {
alert(1);
});
Thanks!
发布评论
评论(3)
首先。什么?这是没有意义的:
它不会像您想象的那样将事件保存到局部变量中。它将对
foobar 元素对象
的引用保存到event
变量中 - 大多数 mootools 元素方法将返回this
进行链接,即元素本身而不是方法的结果(除非它是像“.getStyle”这样的吸气剂)。这取决于你如何摆脱这个元素,接下来会发生什么。首先,
element.destroy
,在这里找到:https://github.com/mootools/mootools-core/blob/master/Source/Element/Element.js#L728它将从 dom 和内存中删除元素,并以安全的方式清空它。一旦它消失,它将依赖于浏览器的 GC 进行清理,mootools 不会为元素本身执行任何壮观的 GC,但它也会在子节点上运行特殊的
clean
函数:varchildren = clean(this).getElementsByTagName('*');
。clean 方法还会删除附加到 div 子元素的任何事件处理程序和存储。
然后。 mootools 添加的事件进入元素存储。元素存储位于元素原型使用的闭包后面的对象中。为了测试它,我们将重新实现它并使其可刺穿(称为存储的全局对象),以便我们可以检查父级消失后引用会发生什么:
http://jsfiddle.net/dimitar/DQ8JU/
这一切证明的是,mootools 可以清理所有你需要清理的东西。只要您不在使用的元素上使用任何内联
onclick=
内容,就可以了。在 mootools 的垃圾收集和浏览器之间,您可以得到很好的保护。请注意,如果回调是匿名的,您可以在单个元素上堆叠多个事件。first of all. what? this makes no sense:
it does not save the event into a local variable as you seem to think. it saves a reference to the
foobar element object
into theevent
variable - most mootools element methods will returnthis
for chaining, which is the element itself and not the result of the method (unless it's a getter like '.getStyle').it then depends on how you get rid of the element what happens next. first off,
element.destroy
, found here: https://github.com/mootools/mootools-core/blob/master/Source/Element/Element.js#L728it will remove the element from the dom and from memory, and empty it in a safe way. it will be reliant on the browser's GC to clean up once it's gone, mootools won't do any spectacular GC for you for the element itself but it does run the special
clean
function on the child nodes as well:var children = clean(this).getElementsByTagName('*');
.the clean method also gets rid of any event handlers and storage attached to the child elements of the div.
THEN. events added by mootools go into element storage. Element storage is in an object behind a closure which the element proto uses. To test it, we will re-implement it and make it puncturable (a global object called storage) so we can check what happens to the reference after the parent is gone:
http://jsfiddle.net/dimitar/DQ8JU/
what all this proves is, mootools cleans up all you need cleaned. as long as you don't use any inline
onclick=
stuff on elements you work with, you're going to be fine. Between mootools' garbage collection and the browser, you are well covered. just be aware you can stack up multiple events on a single element if the callbacks are anonymous.有趣的问题...阅读以下内容:https://developer.mozilla。 org/en/DOM/element.addEventListener#Memory_issues
要使用 jQuery 删除事件侦听器,请参阅 http://api.jquery.com/unbind/
Interesting question... have a read of this: https://developer.mozilla.org/en/DOM/element.addEventListener#Memory_issues
To remove the event listener using jQuery, see http://api.jquery.com/unbind/
我发现旧版本的 IE 似乎在添加和删除大量绑定事件的元素时存在问题。主要原因是循环引用无法被垃圾收集。您可以在此处找到更多信息:http://msdn.microsoft.com/en-us/ library/Bb250448
设置为 null 不会删除该事件,它只会删除对该事件的引用。您需要同时使用 element.removeEventListener 和 element.detachEvent (取决于浏览器),或者如果您使用 jquery unbind 应该可以工作。
此外,还有一些工具可用于检测泄漏,这个工具效果很好(根据同事的说法):http://blogs.msdn.com/b/gpde/archive/2009/08/03/javascript-memory-leak- detector-v2.aspx
I have found that older versions of IE seems to have issues with adding and removing lots of elements with events binded to them. The main cause is circular references that cannot be garbage collected. You can find more information here: http://msdn.microsoft.com/en-us/library/Bb250448
Setting to null will not remove the event, it would just remove the reference to the event. You need to use both element.removeEventListener and element.detachEvent (depending on browser), or if you are using jquery unbind should work.
Also, there are tools available to detect leaks, this one works well (according to coworker): http://blogs.msdn.com/b/gpde/archive/2009/08/03/javascript-memory-leak-detector-v2.aspx