【问题标题】:Object becomes null [closed]对象变为空 [关闭]
【发布时间】:2013-10-09 13:53:10
【问题描述】:

嗨,我们在我们的 android 应用程序中遇到了一个奇怪的问题。在我们的应用程序中,当我们启动应用程序(第一个活动)时,我们将所有需要的对象/数据存储在一个公共对象(称为对象 A)中。我们将上下文本身存储在该对象中。每当我们在应用程序中需要上下文时,我们都会从对象 A 获取上下文并使用它。除以下情况外,所有情况都可以正常工作。

i) 当我们的应用程序处于后台时,我们玩了一些高端游戏。现在我们通过最小化屏幕(最近的应用程序)回到应用程序。突然应用程序崩溃了。
ii) 如果我们通过“设置”强制停止应用程序,并通过最小化屏幕返回应用程序,则会发生同样的崩溃。

在这两种情况下,对象 A 都变为 null(它可能会被 GC 删除),因此依赖于对象 A 的所有操作都会出现异常。

为什么会这样?我们如何防止GC收集对象A?我们如何处理强制停止?请给出任何想法。

【问题讨论】:

  • 您不能强制 GC 或系统杀死您的进程。在这种情况下,您应该找到一种方法来序列化/反序列化您的对象。
  • 这可能是您在编写 Android 应用程序时应该了解的最重要的概念。 developer.android.com/training/basics/activity-lifecycle/…
  • Android(实际上是 Dalvik)不会 GC 单个对象,除非您的应用正在运行并且没有对其的引用。我不知道这个神话是从哪里开始的。您的 app 可能会被杀死,在这种情况下,一切都要从头开始。如果需要保存状态,则使用onPause() 和/或onStop() 进行序列化。请注意,onDestroy() 仅在您 finish() 活动时才有用。顺便说一句,如果您存储的 contextActivity 上下文,那么您做错了。

标签: java android performance garbage-collection


【解决方案1】:

为什么会这样?

其他应用程序也需要内存才能运行。假设 Android 会将您的数据无限期地保存在内存中是不合理的。

我们如何防止GC收集对象A?

不要。为您的问题找到不同的解决方案。

我们如何处理强制停止?请给出任何想法。

最终,由您决定,但这里有一些常见的选择:

  • 当存储的数据不再存在时,将其视为应用程序的全新启动。将用户带到着陆页并让他开始新游戏。
  • 保留数据。根据您存储的内容,SharedPreferences 或 SQLite 可能是不错的选择。请参阅 Storage Options 了解您的存储选项摘要。

第二个选项显然不适用于您的 Context,但无论如何我可能会为 Context 设计一个不同的解决方案。

【讨论】:

    【解决方案2】:

    您最好使用应用程序上下文! 只需在您的 Activity 中使用 getApplicationContext() 并改用它即可。 否则,一旦系统需要内存,您的活动就会泄漏。

    您的 Activity 在按下 home 时进入后台, 然后在玩视频游戏或消耗内存的应用程序时,系统会释放您的活动。

    尝试理解 Activity Lifecycle 来解决这个问题:

    此外,当在“普通”java 中看到它时,您的活动 Wrapped 对象会被GC 收集,只要它符合条件,即它不再被任何其他对象引用。如果您的整个应用程序在系统需要内存时被释放,这是无法避免的。 尝试检查 onResume() 中的 null 并再次重新实例化您的对象!

    希望对你有帮助。

    【讨论】:

      猜你喜欢
      • 2012-12-03
      • 2014-01-01
      • 2013-11-08
      • 1970-01-01
      • 1970-01-01
      • 2016-02-17
      • 2015-03-04
      • 1970-01-01
      • 2020-01-04
      相关资源
      最近更新 更多