Activity启动模式

来源:互联网 发布:淘宝差价链接怎么做 编辑:程序博客网 时间:2024/06/05 18:37

 Activity启动模式

这一章主要和大家讲解Activity的启动模式,首先我们先抛出一个问题(为什么要使用启动模式?)。我们知道,当我们使用默认启动模式时,我们多次启动同一个Activity,系统就会重复创建多个实例,这样做法肯定是有问题的(重复创建首先内存资源浪费了,再者重复创建如果该Activity是网络数据展示则会导致流量的浪费),基于上述问题系统为我提供了四种启动模式:standard,singleTop,singleTask,singleInstance。

注:【任务栈:是一种“先进后出”的栈结构,当栈中没有Activity的时候,系统会回收这个任务栈。】

㈠standard标准模式(普通模式):这也是系统默认的模式,每次启动一个Activity都会重新创建该实例,同样生命周期OnCreate、OnStart、OnResume都会被重新调用。这个模式的Activity栈依附于启动它的Activity(谁启动了它,它就在谁的栈中)。但是有一种错误做法,例如我们使用Application的Context启动该模式的Activity系统则会报错,非让我们在启动模式中加入FLAG_ACTIVITY_NEW_TASK。原因是Application的Context没有所谓的任务栈,故启动这个模式的activity没有地方存放,因此要求新建一个栈用于存放。


脑洞时刻:A是标准模式,B启动A,A是否会在B的任务栈中?

 <application        android:allowBackup="true"        android:icon="@drawable/ic_launcher"        android:label="@string/app_name"        android:theme="@style/AppTheme" >        <activity            android:name="com.example.acrivitylaunchmodedemo.MainActivity"            android:label="@string/app_name" >        </activity>        <activity            android:name="com.example.acrivitylaunchmodedemo.Activity_2"            android:label="@string/title_activity_activity_2"            android:launchMode="singleTask"            android:taskAffinity="com.example.text1" >            <intent-filter>                <action android:name="android.intent.action.MAIN" />                <category android:name="android.intent.category.LAUNCHER" />            </intent-filter>        </activity>    </application>
//按键启动MainActivity
case R.id.bu_startactivity:Intent intent = new Intent();intent.setClass(this, MainActivity.class);startActivity(intent);break;
通过adb shell dumpsys activity命令可以看出activity栈的信息


通过上述信息可以看出:

任务栈:com.example.text1,其中有两个Activity(com.example.acrivitylaunchmodedemo/.Activity_2 & com.example.acrivitylaunchmodedemoMainActivity),故B启动标准模式的A,A就依附于B的任务栈中了。

㈡singleTop栈顶复用模式:在这种模式下,如果新Activity已经位于任务栈的栈顶,那么此Activity不会重新创建,同时它的生命周期会执行onNewIntent()方法,onCreate、onStart不会执行,如果新Activity不在栈顶则还是会重新创建。

脑洞时刻:目前栈内情况为ABC,其中ABC为三个Activity,这时再启动ActivityA,。结果如下图:


脑洞时刻目前栈内情况为ABC,其中ABC为三个Activity,这时再启动ActivityC,。结果如下图:


测试APK,栈信息图:

注:测试APK都使用栈顶复用模式,有三个Activity首先启动Activity_1,再次启动Activity_2、Activity_3最后启动Activity_1。

从上面分析得出:由于Activity_1不在栈顶故又重新创建了一个。

㈢singleTask栈内复用模式:这种状况下只要栈中有要启动的Activity,就不会创建新的。和singleTop一样生命周期会执行onNewIntent()方法,onCreate、onStart不会执行。当启动一个singleTask的Activity时,首先系统寻找是否有该Activity的栈,如果有,看其中有没有和该Activity相同的Activity,没有创建,有不创建。如果没有该Activity的栈先创建栈再创建该Activity。


singleTask还具有CleanTop的效果(你启动的Activity栈中有而且不处于栈顶,则他会移除它上面的所有的Activity):我还是以SingTop代码栗子做演示让大家看结果(我将把SingleTop栗子的启动模式改为singleTask

从上面信息可以看出,最后我们启动Activity_1时,栈中情况是只有Activity_1一个Activity,它上面的Activity_2、Activity_3均被移出栈。

singleInstance单实例模式:这是一种加强的singleTask除了具备singleTask的功能,还有该种模式下的Activity只能单独存在一个任务栈中,由于栈复用的特性,后续的请求不会受理,除非这个栈被系统销毁。例如A_1”B也是_1”,启动AB后任务中有两个_1”分别装的AB

基于“例如”我修改测试APK启动模式,还是SingTop的栗子,结果如图:

从上述信息可以看出:三个Activity都是相同栈名,但是栈不一样没有栈中都存在一个Activity。当启动Activity_1时没有新创建。
脑洞时刻有四个Activity(普通模式Activity_1)、(singleTask Activity_2)、(SingTop Activity_3) 操作步骤:1启动2 --> 2启动3 --> 3启动1 --> 1启动2 back键回到哪个Activity?

谢谢品读!
2 0
原创粉丝点击