Javascript 在SAPUI5/OpenUI5中创建和删除视图时内存泄漏

Javascript 在SAPUI5/OpenUI5中创建和删除视图时内存泄漏,javascript,memory-leaks,sapui5,Javascript,Memory Leaks,Sapui5,我正在使用OpenUI5/SAPUI5编写一个测试应用程序,即使经过大量的测试、优化和研究,我似乎仍然存在内存泄漏 我有几个带有控制器的视图,并使用SAPUI5的SplitApp控件在它们之间导航。每当我向后导航时,我都会像这样破坏视图: // Get current page var sCurrentDetailPage = this.oSpiltApp.getCurrentDetailPage().getId(); // Go back this.oSpiltApp.backDetail()

我正在使用OpenUI5/SAPUI5编写一个测试应用程序,即使经过大量的测试、优化和研究,我似乎仍然存在内存泄漏

我有几个带有控制器的视图,并使用SAPUI5的SplitApp控件在它们之间导航。每当我向后导航时,我都会像这样破坏视图:

// Get current page
var sCurrentDetailPage = this.oSpiltApp.getCurrentDetailPage().getId();
// Go back
this.oSpiltApp.backDetail();
this.oSpiltApp.removeDetailPage(sCurrentDetailPage);
// Destroy current page
sap.ui.getCore().byId(sCurrentDetailPage).destroy(true);
由于我无法删除视图维护的所有内容,我在控制器的onExit函数中手动添加了对元素的destroy调用(在销毁视图时调用onExit)。尽管对视图的destroy调用也应该销毁它的子对象,但这似乎去除了更多的元素,但仍然不够。 我只使用SAPUI5提供的事件和单击处理程序,调用destroy时应该分离这些处理程序,如果视图订阅了某个事件,我将在onExit中取消订阅

问题:

如果我创建并导航到一个新视图,然后返回(销毁该视图),则分配的内存中只有大约一半似乎再次被释放。例如,我会打开一个视图,返回并在Chrome中拍摄一个堆快照,其中显示了20MB。然后我打开和关闭同一个视图5次,最后得到20.5MB。因此,对于此特定视图,销毁时不会删除100KB。如果应用程序一整天都在使用(按计划),这可能会在较旧的移动设备上造成问题。 有人有过这个问题的经验吗?多谢各位

编辑

我用Chrome时间表记录了内存使用情况。我反复创建了两个视图,并再次销毁了它们。对于JS堆,我得到了以下结果:

因此,它似乎随着时间的推移而大量增长

对于节点和侦听器,我得到了这个结果,这对我来说似乎没什么问题:


你会说这是内存泄漏还是我反应过度?这个测试可靠吗?非常感谢。

浏览器保留内存是正常的。JavaScript是一种垃圾收集语言,因此清空对象引用或使用
delete
键盘不会触发垃圾收集器释放内存

现代浏览器中的内存垃圾收集通常分为两个阶段:

  • 检查对象图。任何未被“全局上下文”中任何内容引用的对象(例如浏览器中的
    窗口
    对象)都标记为“过时”

  • 下次运行垃圾收集器时,所有以前“过时”的对象都会释放内存并返回供浏览器使用——请注意,从操作系统的角度来看,此内存不会“释放”。浏览器会保留这些内存地址,以防再次需要它们

  • 释放“过时”对象后,浏览器再次返回步骤1,将下一批对象标记为“过时”

  • 此外,大多数浏览器只允许垃圾收集器运行设定的毫秒数,因为在此期间,浏览器中的UI在技术上是无响应的,因此正在检查的对象图不会在运行中发生变化

    内存泄漏的真正测试是利用内置的浏览器工具进行内存分析。我知道Chrome和Firefox都有这个功能。其次,随着时间的推移——我的意思是超过10到15分钟——您应该会看到分配给浏览器的内存出现锯齿状模式,其中短期趋势是上升和下降的,但总体趋势是平的

          .      .      .      .      .
        . |    . |    . |    . |    . |
      .   |  .   |  .   |  .   |  .   |
    .     |.     |.     |.     |.     |
    
    如果您看到一段时间内呈锯齿状,总体趋势是向上的,那么这可能表明内存泄漏

                                     .
                            .      . |
                   .      . |    .   |
          .      . |    .   |  .     |
        . |    .   |  .     |.       
      .   |  .     |.       
    .     |.
    

    真正的测试是使用浏览器附带的内置性能监视工具。

    非常感谢您的回答。如果我理解正确,我不应该在Chrome中使用堆快照,因为它不会显示内存是否已释放。所以更好的工具可能是Chrome开发者工具中的时间线,对吗?我用一些显示时间线的截图更新了我的初始帖子。如果你能看一看,那就太酷了。再次感谢:-)我注意到了以下问题:你可能有类似的问题吗?@user3783327谢谢你的意见。在我的例子中,即使没有加载数据,视图在被销毁后似乎仍然占据了大约150KB的空间。所以我的问题不仅仅是数据。但当我试图删除数据时,我会检查数据发生了什么。