Activity和Servlet一样,都用了回调机制。我们通过类比servlet来学习Activity。当一个servlet开发出来之后,该servlet运行于Web服务器中。服务器何时创建servlet的实例,何时调用servlet的方法向用户生成响应,程序员无法控制,这种回调由服务器自行决定。Activity也一样,被开发出来,开发者只要在AndroidManifest.xml文件配置该Activity即可。至于该Activity何时被实例化,它的方法何时被调用,对开发者来说完全是透明的。
当开发者开发一个Servlet时,根据不同的需求场景,可能需要选择性的的实现如下方法:
- init(servletConfig config)
- destroy()
- doGet(HttpServletRequest req,HttpServletResponse resp)
- doPost(HttpServletRequest req,HttpServletResponse resp)
- sevice(HttpServletRequest req,HttpServletResponse resp
- 当把Servlet部署到Web应用中之后,Web服务器将会在特定的时刻,调用该Servlet上面的各种方法---这种调用就被称为回调。
Activity的回到机制与此类似,当Activity被部署到Android应用之后,随着应用程序的运行,Activity会不断的在不同的状态进行切换,该activity中特定的方法就会被回调-----开发者就可以选择性的重写这些方法来加入业务相关的处理。Android运行过程的不同状态被称为生命周期。
Android的生命周期:当activity处于Android的应用中的运行时,它的活动状态由Android运行时以Activity栈的形式管理。当前活动的Activity位于栈顶。
Android的生命周期演示:android大致经过如下四个状态:
- 活动状态:当前Activity位于前台,用户可见,可以获得焦点。
- 暂停状态:其他Activity位于前台,该Activity依然可见,只是不能获得焦点。
- 停止状态:该Activity不可见,失去焦点
- 销毁装填:该activity结束,或者activity所在的Dalvik进程被结束。
下面是官方API所提供的生命周期图:

下面使用代码亲自测下Android的生命周期,测完就明白了:
package com.lp.ecjtu.activitydemo1;
import android.os.Bundle;
import android.app.Activity;
import android.util.Log;
import android.view.Menu;
import android.widget.EditText;
public class MainActivity extends Activity {
private static final String TAG = "MainActivity";
private EditText editText;
//创建Activity被回调
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
editText = (EditText) findViewById(R.id.editText);
Log.e(TAG, "Start onCreate =========");
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
//启动Activity被回调
@Override
protected void onStart() {
// TODO Auto-generated method stub
super.onStart();
Log.e(TAG, "Start onStart =========");
}
//重新启动Activity被回调
@Override
protected void onRestart() {
// TODO Auto-generated method stub
super.onRestart();
Log.e(TAG, "Start onRestart =========");
}
//恢复Activty被回调
@Override
protected void onResume() {
// TODO Auto-generated method stub
super.onResume();
Log.e(TAG, "Start onResume =========");
}
//暂停Activity被回调
@Override
protected void onPause() {
// TODO Auto-generated method stub
super.onPause();
Log.e(TAG, "start onPause=============");
}
//停止Activity被回调
@Override
protected void onStop() {
// TODO Auto-generated method stub
super.onStop();
Log.e(TAG, "start onStop=============");
}
//销毁Activity被回调
@Override
protected void onDestroy() {
// TODO Auto-generated method stub
super.onDestroy();
Log.e(TAG, "start onDestroy=============");
}
}
运行上面的代码:我们打开应用程序时回调了OnCreate()-->onStart()-->onResume()方法。在LogCat窗口可以看到:

Back键:当我们按返回键的时候这个应用程序或者Activity将结束,依次回调了OnPause()-->onStop()-->Ondestroy()方法:在LogCat窗口可以看到:

HOME键:当我们正在打游戏的时候,突然来了条短信,我们想看短息,按HOME键,然后打开短信的应用,当我们按HOME键的时候Activity先后执行了OnPause()-->OnStop方法,在LogCat窗口可以看到:

而我们看完短息在启动应用的时候:会执行OnRestart()-->onStart-->OnResume方法。在LogCat窗口可以看到:
![]()
通过上面的操作,想必我们都对Android Activity生命周期有了深刻的了解,我们就可以在开发Activity的时候,选择性的重写生命周期的方法来解决业务上的一些需求。
例如:下面的这个例子,当我们在看视屏的时候,或者在注册的时候,刚好填完用户的注册信息,不小心按到了Home键,当我们在进入应用程序的时候,发现之前填的注册信息全没了,这时候我们就要哭了,说明这个应用程序做的比较垃圾。正常情况下,我们之前填写的注册信息还在,也就是说和我们按Home键之前的状态是一致的。
为了理解,我们用一个小例子说明问题:
在XML代码代码中增加EditText:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context=".MainActivity"
android:orientation="vertical">
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="@string/hello_Activity" />
<EditText
android:id="@+id/editText"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:ems="10" />
</LinearLayout>
java代码不变,运行程序,在EditText中输入peter,

然后按HOME键,在次启动MainActivity,发现之前输入的内容没了。

这显然不是正常的应用程序,我们都会哭的。那么就需要我们队生命周期非常了解了,当我们按Home键的时候,Activity回调了onPause-->OnStop()方法,再次进入应用程序的时候回调了OnRestart-->OnStart-->onResume()方法,说明我们只要在onPause()和OnRestart方法里面做处理既可以保存之前的状态:下面看代码
package com.lp.ecjtu.activitydemo1;
import android.os.Bundle;
import android.app.Activity;
import android.util.Log;
import android.view.Menu;
import android.widget.EditText;
public class MainActivity extends Activity {
private static final String TAG = "MainActivity";
private EditText editText;
//定义一个String字符串用于存放用户输入的字符串
private String userString;
//创建Activity被回调
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
editText = (EditText) findViewById(R.id.editText);
Log.e(TAG, "Start onCreate =========");
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
//启动Activity被回调
@Override
protected void onStart() {
// TODO Auto-generated method stub
super.onStart();
Log.e(TAG, "Start onStart =========");
}
//重新启动Activity被回调
@Override
protected void onRestart() {
// TODO Auto-generated method stub
super.onRestart();
//再次启动应用时,把先前用户输入的值重新设置EditText
editText.setText(userString);
Log.e(TAG, "Start onRestart =========");
}
//恢复Activty被回调
@Override
protected void onResume() {
// TODO Auto-generated method stub
super.onResume();
Log.e(TAG, "Start onResume =========");
}
//暂停Activity被回调
@Override
protected void onPause() {
// TODO Auto-generated method stub
super.onPause();
//按home键的时候,保存用户输入的字符串信息。
userString = editText.getText().toString();
Log.e(TAG, "start onPause=============");
}
//停止Activity被回调
@Override
protected void onStop() {
// TODO Auto-generated method stub
super.onStop();
Log.e(TAG, "start onStop=============");
}
//销毁Activity被回调
@Override
protected void onDestroy() {
// TODO Auto-generated method stub
super.onDestroy();
Log.e(TAG, "start onDestroy=============");
}
}
重新启动app,按home键,在进入应用程序OK了,看下面的图:

总结:理解生命周期的关键是,我们可以在开发过程选择性的重写生命周期中的方法,解决一些实际问题,这才是关键,学以致用!
