gpt4 book ai didi

android - 在 onPause 而不是 onDestroy 中释放资源

转载 作者:塔克拉玛干 更新时间:2023-11-01 21:57:42 26 4
gpt4 key购买 nike

这是关于 POST-honeycomb(即 Android 3.0+)的,下面的引用来自 https://developer.android.com/reference/android/app/Activity.html

根据生命周期,onStop 和 onDestroy 是可杀死的,这意味着:

Note the "Killable" column in the above table -- for those methods that are marked as being killable, after that method returns the process hosting the activity may be killed by the system at any time without another line of its code being executed

  1. 换句话说,onStop(以及在此事件之前发生的其他事件)保证被调用,但在方法返回的那一刻,进程可能会终止,因此 onDestroy 是不保证会被调用。

    另一段引述:

    For those methods that are not marked as being killable, the activity's process will not be killed by the system starting from the time the method is called and continuing after it returns.

    紧随其后

    Thus an activity is in the killable state, for example, between after onPause() to the start of onResume().

  2. 但这对应于上面所说的,除非这只对应于PRE-honeycombPOST-honeycomb 不是这样,对吧?所以基本上,onPause 和 onStop 都可以保证被调用。

  3. 假设我只在 onDestroy 中释放一个资源,那么这可能会导致泄漏,因为 onDestroy 可能不会被调用,对吧?

  4. 但是,当进程被 android 本身杀死时,这种情况(即不调用 onDestroy)是否会发生之外?是否有其他场景导致onDestroy不被调用,从而泄露资源

  5. 当 Android 终止进程时,资源将被销毁并且不会发生泄漏(即使我们没有显式释放资源?)是真的吗?

请提供这些陈述 (1) (2) (3) (4) (5) 是否正确的详细信息。

最佳答案

首先让我们了解一下您引用的文档是怎么回事。

以下命令显示 AOSP 中 Activity.java 文件的 git blame 输出:

$ cd $AOSP/frameworks/base
$ git blame ./core/java/android/app/Activity.java

输出的相关部分:

9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800  363)  * <p>Note the "Killable" column in the above table -- for those methods that
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 364) * are marked as being killable, after that method returns the process hosting the
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 365) * activity may killed by the system <em>at any time</em> without another line
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 366) * of its code being executed. Because of this, you should use the
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 367) * {@link #onPause} method to write any persistent data (such as user edits)
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 368) * to storage. In addition, the method
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 369) * {@link #onSaveInstanceState(Bundle)} is called before placing the activity
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 370) * in such a background state, allowing you to save away any dynamic instance
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 371) * state in your activity into the given Bundle, to be later received in
550116576 (RoboErik 2014-07-09 15:05:53 -0700 372) * {@link #onCreate} if the activity needs to be re-created.
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 373) * See the <a href="#ProcessLifecycle">Process Lifecycle</a>
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 374) * section for more information on how the lifecycle of a process is tied
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 375) * to the activities it is hosting. Note that it is important to save
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 376) * persistent data in {@link #onPause} instead of {@link #onSaveInstanceState}
5c40f3fcc (Daisuke Miyakawa 2011-02-15 13:24:36 -0800 377) * because the latter is not part of the lifecycle callbacks, so will not
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 378) * be called in every situation as described in its documentation.</p>
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 379) *
0aae2d4e0 (Dianne Hackborn 2010-12-07 23:51:29 -0800 380) * <p class="note">Be aware that these semantics will change slightly between
0aae2d4e0 (Dianne Hackborn 2010-12-07 23:51:29 -0800 381) * applications targeting platforms starting with {@link android.os.Build.VERSION_CODES#HONEYCOMB}
0aae2d4e0 (Dianne Hackborn 2010-12-07 23:51:29 -0800 382) * vs. those targeting prior platforms. Starting with Honeycomb, an application
0aae2d4e0 (Dianne Hackborn 2010-12-07 23:51:29 -0800 383) * is not in the killable state until its {@link #onStop} has returned. This
0aae2d4e0 (Dianne Hackborn 2010-12-07 23:51:29 -0800 384) * impacts when {@link #onSaveInstanceState(Bundle)} may be called (it may be
0aae2d4e0 (Dianne Hackborn 2010-12-07 23:51:29 -0800 385) * safely called after {@link #onPause()} and allows and application to safely
0aae2d4e0 (Dianne Hackborn 2010-12-07 23:51:29 -0800 386) * wait until {@link #onStop()} to save persistent state.</p>
0aae2d4e0 (Dianne Hackborn 2010-12-07 23:51:29 -0800 387) *
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 388) * <p>For those methods that are not marked as being killable, the activity's
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 389) * process will not be killed by the system starting from the time the method
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 390) * is called and continuing after it returns. Thus an activity is in the killable
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 391) * state, for example, between after <code>onPause()</code> to the start of
9066cfe98 (The Android Open Source Project 2009-03-03 19:31:44 -0800 392) * <code>onResume()</code>.</p>

请注意,讨论 Honeycomb 后行为的段落是由 Dianne Hackborn 于 2010-12-07 添加的,而封闭段落可追溯到 2009-03-03。

它告诉我们的是 Dianne 添加了新段落而没有更新 javadoc 的其余部分,因此矛盾。不幸的是,这在 Android 中并不少见。

您的问题:

1) 在 Android 的后 Honeycomb 版本上,onResume()onStop() 都保证被调用(正如 Dianne Hackborn 在她对 Activity 的补充中所说的) javadoc)。

2) 在 pre-Honeycomb 上只有 onPause() 保证被调用(如 Activity 的 javadoc 的早期版本所述)

3,4,5) onDestroy() 只有在托管整个应用程序的进程被终止时才会被调用。当进程被终止时,分配给它的所有资源都被释放,因此在这种情况下不存在内存泄漏的风险。

重要说明:由于在 onDestroy() 中释放资源不会导致内存泄漏,因此将所有“释放”代码放在那里看起来是个好主意。但是,它很少是最佳方法。为什么?阅读下文。

Activity 进入后台时,它会停止,但不会被销毁(通常)。 Activity 可以长时间保持这种“停止”状态,如果用户返回应用程序,它将再次启动。如果你在 onDestroy() 中释放资源,当 Activity 进入后台时默认情况下不会调用它,Activity 将持有这些资源,同时处于停止状态,从而导致您的应用在后台状态下消耗更多资源。

当 Android 内存不足时,它会开始终止进程​​以释放它们消耗的内存。选择要终止的进程时要考虑的最重要的考虑因素之一是它们的资源消耗。因此,如果您的应用在后台停止状态下持有资源,则它被 Android 杀死的可能性更高。

此外,作为开发者,我们必须确保为用户制作最好的应用。在后台消耗非最小用户手机资源和电池的应用程序不是一个好的应用程序。用户会知道的!

因此,我强烈建议在onStop() 方法中释放所有资源。我通常根本不会覆盖 ActivitiesFragments 中的 onDestroy() 方法。

推论:正如@Juan 在他的评论中所指出的,上面的重要说明有一个同样重要但不那么明显的推论:onStart() 应该是分配资源的唯一方法。无论您对“资源”的定义是什么,onCreate()onResume() 都不应该分配这些资源。

关于android - 在 onPause 而不是 onDestroy 中释放资源,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/43412630/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com