Android的4种启动模式

本文详细介绍了Android中四种启动模式:standard、singleTop、singleTask和singleInstance的特点及使用场景。通过具体的示例,展示了不同模式下Activity启动和任务栈的变化过程。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

启动模式简介:

1. standard:

每次启动都会创建一个新的实例,一个任务栈可以有多个实例,每个实例也可以属于不同的任务栈

2. singleTop:

栈顶复用。如果活动在栈顶,再次想创建该活动,不会创建新的Activity,同时会回调onNewIntent,通过该函数可以获得请求的信息

3. singleTask:

栈内复用,这是一种单例模式。只要Activity在一个栈中存在,多次调用都不会重新创建实例,也会回调onNewIntent,分5种情况

a) 目前任务栈S1中有ABC,这个时候Activity  D以singleTask模式请求启动,其所需要的任务栈为S2,由于S2和D的实例都不存在,所以先创建任务栈S2,然后再创建D的实例并将其入栈到S2,S1此时为ABC,S2为D

b) 目前任务栈S1中有ABC,D以singleTask模式请求启动,其所需要的任务栈为S1,由于S1已经存在,所以直接创建D的实例并将其入栈到S1,S1此时为ABCD

c) 目前任务栈S1中有ADBC,D以singleTask模式请求启动,其所需要的任务栈为S1,根据复用原则B和C出栈,D位于栈顶,此时S1为AD

4. singleInstance:

单实例模式。全局单例,当以singleInstance模式创建一个Activity时,会单独创建一个任务栈,然后在该任务栈中创建该Activity,该任务栈只能存在一个Activity

例子:

3个Activity,分别为A、B、C

1.  A为standard,B、C为singleInstance

同时设置B、C的任务栈为com.example.sun.task1,A在默认任务栈

设默认任务栈为S1,设com.example.sun.task为S2

[java]  view plain  copy
  1. <activity android:name=".A">  
  2.     <intent-filter>  
  3.         <action android:name="android.intent.action.MAIN" />  
  4.   
  5.         <category android:name="android.intent.category.LAUNCHER" />  
  6.     </intent-filter>  
  7. </activity>  
  8. <activity android:name=".B"  
  9.     android:taskAffinity="com.example.sun.task1"  
  10.     android:launchMode="singleTask"/>  
  11. <activity android:name=".C"  
  12.     android:taskAffinity="com.example.sun.task1"  
  13.     android:launchMode="singleTask"/>  

启动顺序:A → B → C → A → B

退出顺序:B → A → 桌面(按两次返回键)

a)  A → B → C:

启动A:A的taskAffinity继承自包名,创建默认任务栈(即S1),然后将在S1中创建A,S1为前台任务栈

启动B:根据singleTask的启动原则a点,因为没有任务栈S2,创建任务栈S2,然后创建B,

             此时有两个任务栈S1,S2。因为此时运行B,S2为前台任务栈。

启动C:根据singleTask的启动原则b点,因为存在任务栈S2,直接创建任务栈S2,然后创建 C,

             此时有两个任务栈S1,S2。因为此时运行C,S2为前台任务栈。如下图所示


在terminal输入adb shell dumpsys activity,找到Running activities

可以看到C,B在com.example.sun.task1(即S2)中,A在com.example.sun.webtest(即S1)中,其他不用管

b)  A → B → C → A:

再启动A,因为是C启动A,并且A为standard,会把A创建在C的任务栈中,并位于栈顶


c)  A → B → C → A → B:

从A中启动B,因为B为singleTask,不会创建新的实例,根据singleTask的原则c点,把A、C出栈


 

d) 退出顺序:B → A → 桌面

此时再按返回,B从S2中出栈,S2任务栈不存在了,此时只能切换到后台任务栈S1,显示A,

再次按返回键,A从从S1中出栈,就回到了桌面

2.  A、B、C为singleInstance

同时设置A的任务栈为com.example.sun.task1,BC的任务栈为com.example.sun.task2

设com.example.sun.task1任务栈为S1,com.example.sun.task2任务栈为S2

[java]  view plain  copy
  1. <activity android:name=".A"  
  2.     android:taskAffinity="com.example.sun.task1"  
  3.     android:launchMode="singleTask">  
  4.     <intent-filter>  
  5.         <action android:name="android.intent.action.MAIN" />  
  6.   
  7.         <category android:name="android.intent.category.LAUNCHER" />  
  8.     </intent-filter>  
  9. </activity>  
  10. <activity android:name=".B"  
  11.     android:taskAffinity="com.example.sun.task2"  
  12.     android:launchMode="singleTask"/>  
  13. <activity android:name=".C"  
  14.     android:taskAffinity="com.example.sun.task2"  
  15.     android:launchMode="singleTask"/>  

启动顺序:A → B → C → A → B

退出顺序:B → A → 桌面(按两次返回键)

这里结果是和上面一样的,但任务栈的内容不一样,因为A为singleTask,具体分析如下:

a)  A → B → C:(基本和前面一样)

启动A:根据singleTask的启动原则a点,因为没有任务栈S1,创建任务栈S1,然后将在S1中创建A,S1为前台任务栈,

启动B:根据singleTask的启动原则a点,因为没有任务栈S2,创建任务栈S2,然后创建B,

             此时有两个任务栈S1,S2。因为此时运行B,S2为前台任务栈。

启动C:根据singleTask的启动原则b点,因为存在任务栈S2,直接创建任务栈S2,然后创建 C,

             此时有两个任务栈S1,S2。因为此时运行B,S2为前台任务栈,如下图所示


b)  A → B → C → A:

再启动A,因为A为singleTask,不会把A创建在C的任务栈中,而是切换S1为前台任务,S2变为后台任务

    

c)  A → B → C → A → B:

启动B,因为B为singleTask,根据singleTask的原则c点,把C出栈,同时S1变为后台任务,S2变为前台任务



d) 退出顺序:B → A → 桌面(按两次返回键)

此时再按返回,B从S2中出栈,S2任务栈不存在了,此时只能切换到后台任务栈S1,显示A,

再次按返回键,A从从S1中出栈,就回到了桌面


如果例子2中,设置了A第一次启动B,第二启动C,即A → B → C → A → C,此时退出顺序为C → B → A,因为从A启动C 后,C在S2的栈顶,直接将前台任务切换到S2,不会将任何活动出栈

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值