【问题标题】:How to prevent memory leak in android?如何防止android中的内存泄漏?
【发布时间】:2019-02-12 06:32:37
【问题描述】:

几个月前,我开始在 android 中编程,做我的第一个应用程序,其中包括像服务员应用程序一样接受订单。

因为它是第一个应用程序,你可以想象我的目标不是优化,但这是一个很大的错误。我已经在一些餐厅部署了应用程序,到目前为止一切顺利。

问题:

现在该应用程序安装在一家餐厅,他们为一张桌子接受大量订单,他们最多可以在 10 分钟内接受订单,昨天我接到一个电话,他们说应用程序崩溃了有很多人的桌子。

现在我正在尝试模拟我公司发生的事情。

应用程序:

该应用程序由主屏幕组成,用户可以在其中选择输入设置或订单,然后是另一个“登录”活动,然后是“主”屏幕,其中有一个询问桌子数量的警报然后服务员接受订单并发送。 发送后,我只是通过清除项目中的 recyclerView 并将所有值设置为 0 来“重置”活动或更好,但我认为它会产生“少量”内存泄漏。

结论:

现在我会尽可能多地提出关于如何提高我的应用程序性能或更好地防止内存泄漏的建议,或者即使有可能在服务员发送收据后以某种方式“重新创建”活动,所以我可以“节省”一些内存或 idk。

其实这里是一个剖析屏幕,我不知道它会不会有帮助

【问题讨论】:

  • 我只是开玩笑地说;我不认为你知道如何使用 TL;DR
  • @NikosHidalgo 它不像摘要那样表示?无论如何,我最好在这一点上取消它,哈哈
  • 字面意思是太长了;没读过,用在长篇文章的末尾,用来总结文章。在您的情况下,它用于总结您的故事中省略的部分,而不是您描述的实际问题。再说一次,我只是做了一个有趣的观察,请不要生气!
  • @NikosHidalgo 很好,现在我知道 TL;DR 的意思了
  • 当涉及到您的问题时,我认为您需要提供一些相关代码,否则请为人们对您的问题投反对票并认为过于宽泛做好准备

标签: android optimization


【解决方案1】:

避免内存泄漏的良好做法恕我直言:

  • 避免在帮助程序或数据类中静态存储 android 上下文
  • 记得在他们的工作完成后注销广播接收器。一个好的做法是在 onResume() 方法中注册并在 onPause() 方法中取消注册
  • 更喜欢在“模型”类中使用 LiveData
  • 使用LeakCanary 库来检测任何潜在的泄漏
  • 小心使用静态变量,记得在对应用程序不再有用时将它们设置为null,这样它们就有资格成为垃圾收集。

您可以在 Medium 上找到有关此主题的有趣 article

【讨论】:

    【解决方案2】:

    首先,您的应用似乎没有CrashReport 库。因此,首先要做的是将Crashlytics 添加到您的应用中。

    使用这款适用于 Android 的强大崩溃报告解决方案,对应用问题进行清晰、可行的洞察

    那么如果你认为你的应用有漏洞,我建议你使用CanaryLeak

    适用于 Android 和 Java 的内存泄漏检测库。

    一旦Crashlytics 到位,您就会知道问题出在哪里。它可以为您提供导致应用程序崩溃的代码行。

    【讨论】:

    • 实际上我还听说过 Crashlytics,但即使我不使用 firebase 作为数据库,我也可以使用它吗?没有firebase身份验证它是否工作?
    • 是的,您可以单独使用 Crashlytics
    【解决方案3】:

    您是否有任何未取消订阅的事件订阅者?这是内存泄漏的常见陷阱。我建议您使用内存分析器来分析内存使用情况。如果你使用的是android studio,这篇文章给你一个介绍:

    https://developer.android.com/studio/profile/memory-profiler

    【讨论】:

      【解决方案4】:

      正如其他人强调的那样,如果没有具体细节,很难知道内存泄漏的原因是什么。 我在北京的餐厅(Lily's American Diners)为 Android 平板电脑编写了应用程序,并且长期与泄密作斗争。问题是您的平板电脑 Android 平板电脑每天运行 14 小时,因此您必须拥有非常强大的架构,这样事情就会泄漏并被操作系统破坏。 1) Canaryleak 和 Crashylytics 是好主意。我用过 ACRA。 2)尽量避免弹出窗口,全局变量,所有明显的东西。 3)我使用后台服务来处理上传数据到服务器,从服务器下载菜单,打印到 POS 打印机。 4)对于网络操作,使用OKHTTP,它让所有的Async网络操作更干净。 5) 对于图像加载,使用 Square Picasso。它使所有图像兑现更清洁。 6) 在你的生命周期架构中,尽量减少活动。我使用 1 个单实例活动来进行初始屏幕初始加载,如果他们选择执行管理器操作、设置等,则使用 1 个单实例活动,然后,有 1 个活动全天运行并处理所有事情。在该活动中,我使用 ViewFlipper 为以下每个操作快速更改“页面”(视图): a) 从菜单中选择项目 b) 显示所选项目的票 c) 展示菜肴的大照片或每道菜的特殊选项 d) 显示成功发送的订单 e) 显示未成功发送的订单 f) 为顾客或服务员显示选择餐桌屏幕,无论是谁。 g) 展示每日特价商品 另一个大问题是持久存储,因此在这类应用程序的长期运行过程中,订单和菜单不会丢失等。我广泛使用了共享偏好。 祝你好运。

      【讨论】:

        【解决方案5】:

        有很多不同的可能性,例如:

        1. 数据库保持打开状态
        2. 数据无法正确封装。
        3. 来自共享偏好

        这些是数据可能泄漏的常见可能性。

        【讨论】:

        • 实际上我确定数据库已关闭,因为我只是在设置中使用它来使用餐厅的所有盘子和用户填充数据库,而在 sharedpreference 中我只是存储设置首选项所以我不'不认为它可能会泄漏
        • 收据数据没有存储在设备上,它们被发送到服务器,当我再次打开表格时,我将通过 Ion 库重新下载它们
        • 使用能够释放内存的garbageCollection 方法。从静态变量也有一些内存泄漏。
        猜你喜欢
        • 2016-07-10
        • 2010-12-20
        • 2011-08-09
        • 2012-03-30
        • 1970-01-01
        • 2010-09-21
        • 2011-12-05
        相关资源
        最近更新 更多