Android Activity生命周期
前言
在Android开发的过程中,有一个特别重要的组件:Activity,它是除了Windows、Dialog和Toast之外我们用户可以直接看到的界面。本文主要记录下研究Activity中的一些感悟。
首先Activity的生命周期总体来说可以分为两种:
- 正常情况下的Activity生命周期
- 异常情况下的Activity生命周期
正常情况下的生命周期
所谓的正常的生命周期是指:在有用户的参与的情况下,Activity经历的生命周期的改变。
首先上一张Activity的生命流程切换的图:
7种状态方法说明
接着对每个方法进行解释说明:
- onCreate()方法:——【此时处于Activity在后台不可见】
表示Activity正在被创建,这是在Android开发中接触的最多的方法,比如常见的setContentView()加载布局资源,对控件和某些数字进行初始化等等。
- onStart()方法:——【此时Activity在后台可见】
表示启动,此时的Activity已经是处于可见状态了,但是还没有出现在前台,所以还不能进行交互。 onResume()方法——【此时Activity在前台且可见】
表示Activity已经可见了,且出现在前台。和onStart()和onResume()方法的都是可见状态,但是onResume()方法表示工作在前台。-
onPause()方法——【此时Activity在前台可见】
表示暂停,当Activity需要跳转到另外一个Activity或者程序即将退出的时候都需要执行这个方法。而且在正常情况下,这个方法仅能持续很小的一段时间,紧接着Android系统会接着调用onStop()方法。此时可以停止动画、存储数据等操作。当新的Activity需要显示出来的时候,必须要当前的Activity的onPause()执行完才行。onStop()方法——【Activity不可见仍内存中】
表示Activity即将终止,此时主要做一些比较耗时的操作,如相关资源回收等。onDestroy()方法——【Activity不可见】
表示Activity即将被销毁,这是Activity的最后一个生命周期,在这里了可以做一些最终资源的回收和资源的释放工作等等。onRestart()方法——【Activity重新可见】
表示Activity正在重新启动,触发条件为从不可见转为可见。比如从当前Activity回到上一个Activity,或者从桌面返回到应用程序中去。
具体场景分析
- Activity启动——Activity可见状态的回调情况:
onCreate()--onStart()--onResume();
- 当打开新的Activity或者从当前Activity返回到桌面:
onPause()--onStop()
- 当再次返回到原Activity(从不可见状态切换到可见状态):
onRestart()--onStart()--onResume()
- 当按下Back键或者退出应用程序:
onPause()--onStop()--onDestroy()
疑难问题
- Activity生命周期中onStart和onResume、onPause和onStop有什么不同?
onStart()方法是表示已经启动Activity但 处于不可见状态。而当生命周期走到onResume()状态的时候,Activity是处于可见状态的,这时就可以与用户进行交互。而onPause()此时仍然是处于可见的状态,当到了onStop()的时候是完全处于不可见的状态了。在实际使用中没有其他区别。
总结来说就是: onStart和onStop是从Activity是否可见的两种状态。而onPause和onResume是Activity是否位于前台。
- 当用户启动一个新的Activity,那么之前Activity的onPause和当前Activity的onResume谁先执行?
onPause方法先执行,只有当前的Activity的onPause执行完毕之后才会执行新的Activity的onResume方法。
异常情况下的生命周期
Android 系统出了会受到用户操作导致正常的生命周期异常结束,还有一些异常情况,比如当Android资源配置改变以及系统内存不足的情况下,Activity可能会被杀死。这个时候的生命周期可能会有一些不同。
资源相关的系统配置发生改变导致Activity被杀死
在默认情况下,如果Activity不做特别处理的话,当系统配置发生改变之后,Activity会被销毁并被重新创建。
当系统配置发生改变的时候,当前Activity会执行完所有的生命周期(包括onPause、onStop、onDestroy),在这个过程中,会调用onSaveIntanceState来保存当前的Activity的状态(比如当前的输入框中的文字,当前的选择内容,当前的页面位置等等),然后会重新加载,即调用onCreate等方法。在这个过程中(onCreate)会检查onSaveIntanceState是否有数据,如果有则证明是异常重新加载。这个时候会在onCreate方法中重新赋值相关内容,而这个过程是调用onRestoreInstanceState。
而关于保存和恢复View中的内容的系统工作流程如下:
首先Activity异常后,会直接调用onSaveInstaenceState保存数据,然后Activity会委托Windows保存数据,接着WWindows会调用上面的顶层容器去保存数据,最后顶层容器再通知每一个子View保存数据。
只有在Activity异常终止的时候才会onSaveInstanceState和onRestoreInstanceState来存储和恢复数据,其他的情况是不会触发这个过程的。
资源内存不足导致低优先级的Activity被杀死
Activity优先级如下:
- 前台Activity——正在和用户进行交互的Activity,其优先级最高。
- 可见但是非前台的Activity——比如Activity中弹出一个对话框,导致Activity可见但是位于前台无法直接和用户进行交互。
- 后台Activity——已经被暂停的Activity,比如已经执行了onStop方法,优先级最低。
当系统内存不足的时候,系统会按照优先级的顺序从低到高的杀死目标Activity的进程,然后通过onSaveInstanceState和onRestoreInstance来存储和恢复数据。
一些后台工作不适合脱离四大组件运行,这样的话进程很快被系统杀死。所以一般的做法是将后台工作放在Services中来保证进程具有一定的优先级,这样进程才不会被轻易的杀死。
当系统的配置发生改变之后,Activity会被重新创建。采用以下方式可以不让Activity重新创建。
可以在AndroidManifest中给Activity指定configChanges属性。
总结
在onPause和onStop中都尽量不需要执行太多的耗时操作。尤其是onPause,只有在onPause执行完毕之后,新的Activity才能显示在前台。所以一般来说耗时的数据存储等工作应该放在onStop中完成。此外,在Activity被异常杀死的时候,会完整的经历onPause,onStop,onDestroy过程。并不是直接就被杀死了。从时序上,onRestoreInstanceState的调用时机是在onStart之后。