I have a div in which I frequently create child divs and later remove them. The insert function looks like this.
var insert = function(container, content) {
content = $(content);
container.append(content);
return content;
};
var newContent = insert($('#container'), '<div>new content</div>');
// later
newContent.remove();
container is a jQuery object. content is a string like <div>new content</div
>. Later, that new content is removed.
The div is properly removed from the dom, but using chrome's profiling feature, I can see memory grow and grow. The profile shows a list of strings, thousands of which are my deleted content. Tracking it down, I see that jquery has a property called fragments.
$.fragments
is a map where the key strings are html fragments (literally <div>new content</div>
is the key string) and the values are DocumentFragment objects.
The DocumentFragment objects contain a property 'native' which contains a value of type 'Detached DOM tree'. And there is my detached object.
It seems like the problem is that jQuery is not flushing this $.fragments
collection. I'm using jQuery 1.7.1.
One possible reason I could see for this is that the keys of the map are html that was inserted, but by the time I get around to deleting the fragment, I've changed the newContent div's attributes.
One possible solution is to keep a pool of unused new content divs and re-use them. I don't really want to do that, but it might be reasonable.
It does look like jQuery is using
$.fragments
to speed up$("<...>")
then.I suppose using
$("<div>").html(...)
would not use the cache, but it's obviously semantically different.You could just try occasionally flushing
$.fragments
yourself and see what happens. I have the gut feeling everything would go just as expected with no ill effects.I don't think jQuery really has a way to track the fragment cache usage itself, and an LRU cache or somesuch would probably be slower, not to mention more trouble implementing.