FileReader之后可以清理内存吗?
FileReader 似乎消耗了所有内存,因为它被重复用于预加载多个 blob,并且从不释放它。有什么已知的方法可以强制它释放消耗的内存吗?将 FileReader 对象及其结果属性设置为 null 似乎不起作用。
更新:
这是一个示例代码(在大文件上测试它,就像电影一样,否则你不会注意到任务管理器中的效果):
<input id="file" type="file" onchange="sliceMe()" />
<script>
function sliceMe() {
var file = document.getElementById('file').files[0],
fr,
chunkSize = 2097152,
chunks = Math.ceil(file.size / chunkSize),
chunk = 0;
function loadNext() {
var start, end,
blobSlice = File.prototype.mozSlice || File.prototype.webkitSlice;
start = chunk * chunkSize;
end = start + chunkSize >= file.size ? file.size : start + chunkSize;
fr = new FileReader;
fr.onload = function() {
if (++chunk < chunks) {
// shortcut - in production upload happens and then loadNext() is called
loadNext();
}
};
fr.readAsBinaryString(blobSlice.call(file, start, end));
}
loadNext();
}
</script>
我每次都尝试创建新的 FileReader 实例,但问题仍然存在。我怀疑这可能是由图案的圆形性质引起的,但我不确定在这种情况下可以使用什么其他图案。
我在 Firefox 和 Chrome 中检查了这段代码,Chrome 似乎处理得更优雅 - 它在每个周期后清除内存并且速度非常快。但讽刺的是,Chrome 根本不需要使用这段代码。这只是一个克服 Gecko 6-FormData + Blob bug 的实验(Bug 649150 - Blob 没有如果通过 FormData 发送,则为文件名)。
FileReader seems to consume all the memory as it is repeatedly used to preload multiple blobs, and never frees it. Any known way to force it to release consumed memory? Setting FileReader object and it's result property to null doesn't seem to work.
UPDATE:
Here is a sample code (test it on a big files, like movie, or you won't notice the effect in task manager):
<input id="file" type="file" onchange="sliceMe()" />
<script>
function sliceMe() {
var file = document.getElementById('file').files[0],
fr,
chunkSize = 2097152,
chunks = Math.ceil(file.size / chunkSize),
chunk = 0;
function loadNext() {
var start, end,
blobSlice = File.prototype.mozSlice || File.prototype.webkitSlice;
start = chunk * chunkSize;
end = start + chunkSize >= file.size ? file.size : start + chunkSize;
fr = new FileReader;
fr.onload = function() {
if (++chunk < chunks) {
// shortcut - in production upload happens and then loadNext() is called
loadNext();
}
};
fr.readAsBinaryString(blobSlice.call(file, start, end));
}
loadNext();
}
</script>
I tried to create fresh FileReader instance every time, but the problem still stays. I suspect that it could be caused by a circular nature of the pattern, but I'm not sure what other pattern can be used in this case.
I checked this code in both Firefox and Chrome and Chrome seems to handle it more gracefully - it purges memory after each cycle and is very fast. But the irony of the situation is that Chrome doesn't need to use this code at all. It's just an experiment to overcome Gecko 6- FormData + Blob bug (Bug 649150 - Blobs do not have a filename if sent via FormData).
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
试试这样:
onloadend 将使您避免与其他读取重叠...(显然,您可以更好地修复增量,但您明白了...)
Try it like this instead:
The onloadend will keep you from overlapping your other reads... (Obviously, you can fix the increment a little better, but you get the idea...)
Bug 已被标记为无效,因为事实证明我实际上没有正确地重新使用 FileReader 对象。
这是一个不占用内存和CPU的模式:
另一个错误报告已提交: https://bugzilla.mozilla.org/show_bug.cgi?id=681479,这是相关的,但不是本例中的邪恶。
感谢凯尔·休伊让我注意到这一点:)
Bug has been marked as INVALID, since it turned out that I wasn't in fact re-using FileReader object properly.
Here is a pattern, which doesn't hog memory and cpu:
Another bug report has been filed: https://bugzilla.mozilla.org/show_bug.cgi?id=681479, which is related, but not the evil in this case.
Thanks to Kyle Huey for bringing this to my attention :)