1、Activity的四种状态

理解Activity的生命周期之前,先理解对android的生命周期的特点进行整理,从而归纳出的Activity的四种活动状态。

那么,通常来说,一个Activity的整个生命周期内,会经历如下的几种状态:


  • 运行状态:

* 当一个Activity位于返回栈栈顶的时候,既是处于这种状态之下。

PS:系统最不愿意回收处于运行状态下的Activity,因为这回给用户造成很糟糕的体验


  • 暂停状态:

* 当一个Activity不再位于栈顶,但却又处于“用户可见”的状态下的时候,既是位于暂停状态。

通常我们理解,一个Activity被另一个Activity“压栈”,而离开栈顶,既是有一个新的“界面视图”进入。

那么什么时候一个Activity会出现不再位于栈顶,却又被用户可见的情况呢?

Android中,并不是所有的活动都会占满整个屏幕,例如新压入栈顶的Activity是一个对话框形式的活动时,前一个Activity则会进入到这种所谓的暂停状态。


暂停状态下的Activity无法响应用户的操作,但仍然是被用户可见的,所以系统仍然不愿意去回收此状态下的Activity。


  • 停止状态:

* 当一个Activity不再位于栈顶,并且不再被“用户可见”的时候,就进入到了停止状态。


PS:处于停止状态的活动最大的特点是:系统仍然为其保存相应的状态和成员变量,但这并不是绝对可靠的。

这是因为位于该种状态下的Activity,在一些其他优先级更高的程序需要内存的时候,系统会选择回收释放掉该状态下的Activity,以提供足够的内存。


所以,如果在你的某个Activity中,如果有一些该活动重新回到栈顶时,需要“重现”的数据的话,

为了避免这种状态下的意外发生,可以选择在onSaveInstanceState()方法中保存信息,在下次活动恢复的时候从onCreate()方法中进行恢复,避免数据丢失。


  • 销毁状态:

* 当一个活动从返回栈中被移除时,就处于销毁状态了。系统最倾向于回收这种活动,以保存手机内存的充足。


2、Activity的7种生命周期方法的理解

前面说到了所谓的四种活动状态,其实就是根据Android的生命周期的各个阶段的特点归纳出来的,所以我们自然也应该理解这7种生命周期的特点,它们分别是:

- onCreate()
* 在一个活动初次被创建时调用.
* 通常应该在这个方法里完成活动的初始化事件,如:加载布局,初始化控件,绑定事件等等..

- onStart()
* 在活动由不可见变为可见时调用.

- onResume()
* 当一个活动准备好和用户进行交互时进行调用。此时的活动一定位于返回栈的顶端,处于运行状态。

- onPause()
* 在系统准备去启动或恢复另一个活动的时候调用。
* 通常在这个方法内将一些消耗CPU的资源释放,以及保存一些关键数据。
* 但该方法内的内容执行速度一定要快,也就是说不要在此方法内做耗时操作,否则会影响新的栈顶活动的使用。

- onStop()
* 在活动完全不可见的时候调用。
* 和onPause的调用特点类似,但最大的不同在于,例如:
从当前活动启动的是一个对话框形式的Activity,onPause会得到调用,而onStop不会调用。

- onRestart()
* 这个方法在活动由停止状态变为运行状态之前调用,也就是重新启动。

- onDestroy()
* 在活动即将被销毁之前调用,调用完毕后该活动进入销毁状态。


3、Activity生命周期图

为了更好的对Android中一个Activity在实际运行过程中,生命周期阶段变化的理解,我们结合官方的说明图加深印象。



从这张图中,我们可以归纳得到以下几种情况:

1、当一个Activity初次被创建时,会经过onCreate → onStart→ onResume,此时该活动便已经压入栈顶,进入到了运行状态。


2、此时如果有另一个Activity来到前台,可分为我们上面说到的两种情况:

  • 新进入前台的是“对话框式”的Activity,此时onPause方法被调用,活动进入到暂停状态。而当活动再次返回时,直接调用onResume方法后恢复到运行状态。
  • 新进入前台的是普通的Activity,此时当前我们的Activity进入到不可见状态,经历onPause→ onStop方法后,进入停止状态;若再次返回,则经历onRestart→ onStart→ onResume后,重新启动进入到运行状态。

3、在Activity执行onStop()方法进入到停止状态后,如果出现“另一个优先级更高的地方需要内存”的情况,进程被杀死,此时如果想要返回,则会重新经历onCreate → onStart→ onResume的过程,从而恢复到运行状态。
4、当执行完onDestory方法后,Activity则会被系统销毁,进入到销毁状态之中了。

4、结合实际代码测试、加深理解 书止于此,理论上 我们对Android中Activity的生命周期已经有了一个较为全面的理解。 但我们不能满足于做一个书面上的巨人,于是我们通过实际的代码来对我们的理解进行一个验证,加深理解。
我们的大体思路是: 1、建立一个MainActivity,用于测试生命周期 2、建立一个普通的Activity,用于测试活动被覆盖进入到不可见状态下的生命周期方法执行情况。 3、建立一个对话框式的Activity,用于测试活动不挤出栈顶,但仍然可见下的情况下的生命周期情况。
根据我们的思路书写代码,首先是MainActivity:
import android.app.Activity;import android.content.Intent;import android.os.Bundle;import android.util.Log;import android.view.View;import android.widget.Button;public class LifeCycleTestMainActivity extends Activity {private final String TAG = "LifeCycleTestMainActivity";private Button start_normal_activity;private Button start_dialog_activity;@Overrideprotected void onCreate(Bundle savedInstanceState) {Log.v(TAG, "onCreate...");super.onCreate(savedInstanceState);this.setContentView(R.layout.life_cycle_main_layout);// 恢复数据if (savedInstanceState != null) {String tempData = savedInstanceState.getString("tempData");// do something...}initView();}private void initView() {start_normal_activity = (Button) this.findViewById(R.id.start_normal_activity);start_dialog_activity = (Button) this.findViewById(R.id.start_dialog_activity);start_normal_activity.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {Intent intent = new Intent(LifeCycleTestMainActivity.this, LifeCycleNormalActivity.class);startActivity(intent);}});start_dialog_activity.setOnClickListener(new View.OnClickListener() {@Overridepublic void onClick(View v) {Intent intent = new Intent(LifeCycleTestMainActivity.this, LifeCycleDialogActivity.class);startActivity(intent);}});}// 保存临时数据,避免活动进入到“停止状态”时,被系统回收,数据消失的问题@Overrideprotected void onSaveInstanceState(Bundle outState) {super.onSaveInstanceState(outState);String tempDate = "some temp data have need saved";outState.putString("tempData", tempDate);}@Overrideprotected void onStart() {Log.v(TAG, "onStart...");super.onStart();}@Overrideprotected void onResume() {Log.v(TAG, "onResume...");super.onResume();}@Overrideprotected void onPause() {Log.v(TAG, "onPause...");super.onPause();}@Overrideprotected void onStop() {Log.v(TAG, "onStop...");super.onStop();}@Overrideprotected void onRestart() {Log.v(TAG, "onRestart...");super.onRestart();}@Overrideprotected void onDestroy() {Log.v(TAG, "onDestroy...");super.onDestroy();}}
布局文件:
<?xml version="1.0" encoding="utf-8"?><RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:layout_width="match_parent"    android:layout_height="match_parent" >    <Button        android:id="@+id/start_normal_activity"        android:layout_width="match_parent"        android:layout_height="wrap_content"        android:text="start normal activity"        android:textSize="20sp" />    <Button        android:id="@+id/start_dialog_activity"        android:layout_width="match_parent"        android:layout_height="wrap_content"        android:layout_below="@id/start_normal_activity"        android:text="start dialog activity"        android:textSize="20sp" />    </RelativeLayout>

接着是NormalActivity与DialogActivity的类文件与布局文件,它们十分基本,只用于测试“activity跳转”时,MainActivity的生命周期变化情况,唯一需要记得就是, 为了让DialogActivity以对话框形式出现,我们再mainfest.xml文件中加以配置:
<activity android:name=".LifeCycleDialogActivity" android:theme="@android:style/Theme.Dialog"/>

搞定,接下来我们运行程序,进行测试: 1、首先是该程序初次运行时,我们查看log日志,得到:

结果与我们从第三部分的流程图中得出的结论一致,初次启动某个Activity时,经历了:onCreate → onStart→ onResume。 从而进入到运行状态,一直处于可见状态下与用户进行交互。
2、直到我们点击了"start_normal_activity"按钮,于是normal activity进入前台,此时我们再次查看日志,得到:



日志打印的结果与我们总结的依旧一致,由于新的”NormalActivity“进入返回栈顶,并且"MainActivity"已经进入到不可见状态。 所以MainActivity此时尽力了:onPause→ onStop的过程,进入了停止状态。
3、此时我们点击回退键,返回MainActivity,再次查看日志:


OK,依旧如我们所想,MainActivity由停止状态恢复到运行状态,经历了:onRestart → onStart→ onResume。
4、这次我们选择点击另一个按钮"start_dialog_activity",于是"DialogActivity"进入到栈顶,并且!MainActivity不再位于栈顶,但其仍然处于可见状态,让我们再次查看日志,看看发生了什么:


验证成功,由于MainActivity虽然不再位于栈顶,但其仍然处于可见状态,所以其经历的过程仅仅为:onPasue。

5、再次点击回退键,返回MainActivity,查看日志:


很高兴,依然与我们料想的一样,从暂停状态中恢复,我们只经历了一步:onResume.

6、我们已经位于我们的主界面"MainActivity",此时再次点击回退键,查看日志:

事实上,我们此时再次点击回退键的时候,我们最直观看到的就是:"屏幕返回到了系统的主界面"。 所以我们不难想到,MainActivity离开栈顶,并且进入了不可见的状态,它自然同样会经历:onPause→ onStop。 而与此同时,实际上这时离开栈顶的MainActivity实际上已经是位于返回栈中唯一的Activity了,
当一个程序的返回栈中已经没有任何活动,我们最通俗的理解也就是"我们已经退出该应用了"。 所以这个时候系统紧接着又执行了onDestroy方法,然后销毁掉了MainActivity。
至此,我们"理解完了Android中Activity的生命周期,退出了应用"。

更多相关文章

  1. Android解惑 - 为什么要用Fragment.setArguments(Bundle bundle)
  2. Android(安卓)-- onWindowFocusChanged
  3. Android(安卓)framework层JNI的使用浅析
  4. 【Android】Could not find XXX.apk!的解决方法
  5. 可以在Android上发定时短信
  6. Android(安卓)TabActivity中的子Tab Activity 无法正常 bindServ
  7. Android(安卓)4.4 webview 架构
  8. 设置背景图时防止图片拉伸的解决方法
  9. APK的安装过程及原理详解

随机推荐

  1. Java基础之数组
  2. JAVA实现 springMVC方式的微信接入、实现
  3. 【Java_SSM】(四)Eclipse中通过maven引入ja
  4. 20162305 实验二 Java面向对象程序设计
  5. jsp权限菜单绑定的基本实现
  6. javaweb--Tomcat>>基于windows 系统源码
  7. request对象和response对象
  8. javadoc生成说明文档
  9. Spring Data+JPA (Maven构建Java工程)
  10. 通俗编程——白话NIO之Buffer