Activity的启动模式:standard、singleTop、singleTask、singleInstance
。这四种模式分别是指什么,网上一大堆,就不说了。下面整理下我对这几种启动模式的认识。
-
为什么要设计这么多种启动模式?
默认启动模式:standard。每次启动Activity都要创建一个实例,开销太大。为了复用原有的实例,所以又添加了singleTop、singleTask、singleInstance
。 -
重新认识三个带“single”的启动模式
single意思是“单个的”。要理解这三个single启动模式,就要理解single后面那个单词的含义。singleTop:single+top,top指的是栈顶,就是强调如果栈顶已经有指定的Activity实例存在了,那么就直接复用栈顶的Activity,而不是新建一个。这样就可以保持栈顶只会有一个指定的Activity。
singleTask:single+task,task指的是任务栈,就是指整个Android系统中只能有一个任务栈含有指定的Activity。当要启动singleTask的Activity时,先寻找该Activity所需的任务栈(由taskAffinity决定Activity所需的任务栈)是否存在,若不存在,则创建一个任务栈和Activity实例,把Activity实例压入栈中。若任务栈已经存在,该栈将被切换成前台任务栈,这时若栈中没有Activity实例,就创建Activity实例并压入栈,若已经含有Activity的实例,则将该Activity实例之上的Activity全部弹出栈,使自身变成栈顶。
singleInstance:single+instance,instance指的是实例,就是指整个Android系统中只能有一个该Activity实例。但与singleTask不同的是,singleInstance要求任务栈中只能含有一个Activity实例,也就是说singleInstance的Activity会独占一个任务栈。当要启动singleInstance的Activity时,先寻找该Activity所需的任务栈(由taskAffinity决定Activity所需的任务栈)是否存在,若不存在创建一个任务栈和Activity实例,把Activity实例压入栈中。若任务栈已经存在,则此时栈中必含有唯一的activity,该activity就是要启动的activity,直接把这个任务栈切换成前台任务栈。
-
从上面可以看出启动模式为singleTask或singleInstance的Activity在整个Android系统中同一时刻只会存在一个实例。
-
taskAffinity 只对 singleTask 和 singleInstance 的Activity有效,对 standard 和 singleTop 的无效。
-
哪个任务栈启动了standard或者singleTop的Activity,该activity就位于哪个任务栈中。哪怕这个任务栈是另一个APP的任务栈也是这样。
-
singleTask或singleInstance的Activity始终处于自己的任务栈中,无论是新建还是复用的情况
-
上述情况都是在没有给Intent设置Flag的情况下发生的。Flag的优先级比manifest中的启动模式高。Intent.FLAG_ACTIVITY_CLEAR_TASK必须和FLAG_ACTIVITY_NEW_TASK搭配使用。如果设置了FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_CLEAR_TASK,如果目标task已经存在,将清空已存在的目标Task,否则,新建一个Task栈,之后,新建一个Activity作为根Activity。Intent.FLAG_ACTIVITY_CLEAR_TASK的优先级最高,基本可以无视所有的配置,包括启动模式及Intent Flag,哪怕是singleInstance也会被finish,并重建。更多和Flag有关的内容可以查阅以下文章:
FLAG_ACTIVITY_NEW_TASK与FLAG_ACTIVITY_CLEAR_TOP的理解纠正
Android-Activity所应该了解的大概就这样。(下)
面试官装逼失败之:Activity的启动模式