Android面试系列文章2018之Android部分Activity篇
<div class="article-info-box">
<div class="article-bar-top">
<span class="time">2018年02月08日 10:46:24</span>
<span class="read-count">阅读数:7194</span>
</div>
<div class="operating">
</div>
</div>
</div>
</div>
<article>
<div id="article_content" class="article_content clearfix csdn-tracking-statistics" data-pid="blog" data-mod="popu_307" data-dsm="post">
<div class="article-copyright">
版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/ClAndEllen/article/details/79257489 </div>
<div class="markdown_views">
<h1 id="android面试系列文章2018之android部分activity篇"><a name="t0"></a>Android面试系列文章2018之Android部分Activity篇</h1>
Android面试系列2018知识总结:
http://blog.csdn.net/ClAndEllen/article/details/79257663
1.Activity生命周期
1.1 Activity的4种状态
running/paused/stopped/killed
running:当前Activity正处于运行状态,指的是当前Activity获取了焦点。
paused:当前Activity正处于暂停状态,指的是当前Activity失去焦点,此时的Activity并没有被销毁,内存里面的成员变量,状态信息等仍然存在,当然这个Activity也仍然可见,但是焦点却不在它身上,比如被一个对话框形式的Activity获取了焦点,或者被一个透明的Activity获取了焦点,这都能导致当前的Activity处于paused状态。
stopped:与paused状态相似,stopped状态的Activity是完全不可见的,但是内存里面的成员变量,状态信息等仍然存在,但是也没有被销毁。
killed:已经被销毁的Activity才处于killed状态,它的内存里面的成员变量,状态信息等都会被一并回收。
1.2 Activity的生命周期分析
Activity启动–>onCreate()–>onStart()–>onResume()
点击home键回到桌面–>onPause()–>onStop()
再次回到原Activity时–>onRestart()–>onStart()–>onResume()
退出当前Activity时–>onPause()–>onStop()–>onDestroy()
想了解Activity生命周期的详情请看以下链接:
https://www.jianshu.com/p/f9da7ecded20?utm_campaign=maleskine&utm_content=note&utm_medium=writer_share&utm_source=weibo
1.3 进程的优先级
前台>可见>服务>后台>空
前台:与当前用户正在交互的Activity所在的进程。
可见:Activity可见但是没有在前台所在的进程。
服务:Activity在后台开启了Service服务所在的进程。
后台:Activity完全处于后台所在的进程。
空:没有任何Activity存在的进程,优先级也是最低的。
2.Android任务栈
任务栈与Activity的启动模式密不可分,它是用来存储Activity实例的一种数据结构,Activity的跳转以及回跳都与这个任务栈有关。详情请看下面的Activity的启动模式。
3.Activity的启动模式
Activity的启动模式,你在初学期间一定很熟悉了吧!不管你是否熟悉还是不熟悉,跟随笔者的思路把Activity的启动模式整理一遍:
问题1:Activity为什么需要启动模式?
问题2:Activity的启动模式有哪些?特性如何
问题3:如何给Activity选择合适的启动模式
问题1:Activity为什么需要启动模式?
我们都知道启动一个Activity后,这个Activity实例就会被放入任务栈中,当点击返回键的时候,位于任务栈顶层的Activity就会被清理出去,当任务栈中不存在任何Activity实例后,系统就回去回收这个任务栈,也就是程序退出了。这只是对任务栈的基本认识,深入学习,笔者会在之后文章中提到。那么问题来了,既然每次启动一个Activity就会把对应的要启动的Activity的实例放入任务栈中,假如这个Activity会被频繁启动,那岂不是会生成很多这个Activity的实例吗?对内存而言这可不是什么好事,明明可以一个Activity实例就可以应付所有的启动需求,为什么要频繁生成新的Activity实例呢?杜绝这种内存的浪费行为,所以Activity的启动模式就被创造出来去解决上面所描述的问题。
问题2:Activity的启动模式有哪些?特性如何
Activity的启动模式有4种,分别是:standard,singleTop,singleTask和singleInstance。下面一一作介绍:
1.系统默认的启动模式:standard
标准模式,这也是系统的默认模式。每次启动一个Activity都会重新创建一个新的实例,不管这个实例是否存在。被创建的实例的生命周期符合典型情况下的Activity的生命周期。在这种模式下,谁启动了这个Activity,那么这个Activity就运行在启动它的那个Activity的任务栈中。比如Activity A启动了Activity B(B是标准模式),那么B就会进入到A所在的任务栈中。有个注意的地方就是当我们用ApplicationContext 去启动standard模式的Activity就会报错,这是因为standard模式的Actiivty默认会进入启动它的Activity所属的任务栈中,但是由于非Activity类型的Context(如ApplicationContext)并没有所谓的任务栈,所以这就会出现错误。解决这个问题的方法就是为待启动的Activity指定FLAG_ACTIVITY_NEW_TASK标记位,这样启动的时候就会为它创建一个新的任务栈,这个时候启动Activity实际上以singleTask模式启动的,读者可以自己仔细体会。
2.栈顶复用模式:singleTop
在这种模式下,如果新的Activity已经位于任务栈的栈顶,那么此Activity不会被重新创建,同时它的onNewIntent方法被回调,通过此方法的参数我们可以取出当前请求的信息。需要注意的是,这个Activity的onCreate,onStart不会被系统调用,因为它并没有发生改变。如果新的Activity已经存在但不是位于栈顶,那么新的Activity仍然会重新重建。举个例子,假设目前栈内的情况为ABCD,其中ABCD为四个Activity,A位于栈低,D位于栈顶,这个时候假设要再次启动D,如果D的启动模式为singleTop,那么栈内的情况依然为ABCD;如果D的启动模式为standard,那么由于D被重新创建,导致栈内的情况为ABCDD。
3.栈内复用模式:singTask
这是一种单例实例模式,在这种模式下,只要Activity在一个栈中存在,那么多次启动此Activity都不会重新创建实例,和singleTop一样,系统也会回调其onNewIntent。具体一点,当一个具有singleTask模式的Activity请求启动后,比如Activity A,系统首先寻找任务栈中是否已存在Activity A的实例,如果已经存在,那么系统就会把A调到栈顶并调用它的onNewIntent方法,如果Activity A实例不存在,就创建A的实例并把A压入栈中。举几个栗子:
- 比如目前任务栈S1的情况为ABC,这个时候Activity D以singleTask模式请求启动,其所需的任务栈为S2,由于S2和D的实例均不存在,所以系统会先创建任务栈S2,然后再创建D的实例并将其投入到S2任务栈中。
- 另外一种情况是,假设D所需的任务栈为S1,其他情况如同上面的例子所示,那么由于S1已经存在,所以系统会直接创建D的实例并将其投入到S1。
- 如果D所需的任务栈为S1,并且当前任务栈S1的情况为ADBC,根据栈内复用的原则,此时D不会重新创建,系统会把D切换到栈顶并调用其onNewIntent方法,同时由于singleTask默认具有clearTop的效果,会导致栈内所有在D上面的Activity全部出栈,于是最终S1中的情况为AD。
通过以上3个例子,你应该能比较清晰地理解singleTask的含义了。
4.单实例模式:singleInstance
这是一种加强的singleTask模式,它除了具有singleTask模式所有的特性外,还加强了一点,那就是具有此种模式的Activity只能单独位于一个任务栈中,换句话说,比如Activity A是singleInstance模式,当A启动后,系统会为它创建一个新的任务栈,然后A独自在这个新的任务栈中,由于栈内复用的特性,后续的请求均不会创建新的Activity,除非这个独特的任务栈被系统销毁了。
- 总结
上面介绍了4种启动模式,这里需要指出一种情况,我们假设目前有2个任务栈,前台任务栈的情况为AB,而后台任务栈的情况为CD,这里假设CD的启动模式均为singleTask。现在请求启动D,那么整个后台任务栈都会被切换到后台,这个时候整个后退列表变成了ABCD。当用户按back键的时候,列表中的Activity会一一出栈,如下图1所示:
如果不是请求的D而是请求的C,那么情况就不一样了,如下图2所示:
如何指定活动的启动模式呢?在AndroidManifest.xml文件当注册活动的代码中去指定
比如:我要把MainActivity活动的启动模式指定为singleInstance模式
4.scheme跳转协议
Android中的scheme是一种页面内跳转协议,通过自定义scheme协议,可以非常方便的跳转到app中的各个页面,通过scheme协议,服务器可以定制化告诉app跳转到哪个页面,可以通过通知栏消息定制化跳转页面,可以通过H5页面跳转到相应页面等等。
如果你之前没用过,那么请看以下链接进行学习吧:
http://blog.csdn.net/qq_23547831/article/details/51685310
本Markdown编辑器使用StackEdit修改而来,用它写博客,将会带来全新的体验哦:
- Markdown和扩展Markdown简洁的语法
- 代码块高亮
- 图片链接和图片上传
- LaTex数学公式
- UML序列图和流程图
- 离线写博客
- 导入导出Markdown文件
- 丰富的快捷键
快捷键
- 加粗
Ctrl + B
- 斜体
Ctrl + I
- 引用
Ctrl + Q
- 插入链接
Ctrl + L
- 插入代码
Ctrl + K
- 插入图片
Ctrl + G
- 提升标题
Ctrl + H
- 有序列表
Ctrl + O
- 无序列表
Ctrl + U
- 横线
Ctrl + R
- 撤销
Ctrl + Z
- 重做
Ctrl + Y
Markdown及扩展
Markdown 是一种轻量级标记语言,它允许人们使用易读易写的纯文本格式编写文档,然后转换成格式丰富的HTML页面。 —— [ 维基百科 ]
使用简单的符号标识不同的标题,将某些文字标记为粗体或者斜体,创建一个链接等,详细语法参考帮助?。
本编辑器支持 Markdown Extra , 扩展了很多好用的功能。具体请参考Github.
表格
Markdown Extra 表格语法:
项目 | 价格 |
---|---|
Computer | $1600 |
Phone | $12 |
Pipe | $1 |
可以使用冒号来定义对齐方式:
项目 | 价格 | 数量 |
---|---|---|
Computer | 1600 元 | 5 |
Phone | 12 元 | 12 |
Pipe | 1 元 | 234 |
定义列表
-
Markdown Extra 定义列表语法:
项目1
项目2
- 定义 A
- 定义 B 项目3
- 定义 C
-
定义 D
定义D内容
代码块
代码块语法遵循标准markdown代码,例如:
@requires_authorization
def somefunc(param1='', param2=0):
'''A docstring'''
if param1 > param2: # interesting
print 'Greater'
return (param2 - param1 + 1) or None
class SomeClass:
pass
>>> message = '''interpreter
... prompt'''
脚注
生成一个脚注1.
目录
用 [TOC]
来生成目录:
数学公式
使用MathJax渲染LaTex 数学公式,详见math.stackexchange.com.
- 行内公式,数学公式为: Γ(n)=(n−1)!∀n∈N Γ ( n ) = ( n − 1 ) ! ∀ n ∈ N 。
- 块级公式:
更多LaTex语法请参考 这儿.
UML 图:
可以渲染序列图:
或者流程图:
离线写博客
即使用户在没有网络的情况下,也可以通过本编辑器离线写博客(直接在曾经使用过的浏览器中输入write.blog.csdn.net/mdeditor即可。Markdown编辑器使用浏览器离线存储将内容保存在本地。
用户写博客的过程中,内容实时保存在浏览器缓存中,在用户关闭浏览器或者其它异常情况下,内容不会丢失。用户再次打开浏览器时,会显示上次用户正在编辑的没有发表的内容。
博客发表后,本地缓存将被删除。
用户可以选择 把正在写的博客保存到服务器草稿箱,即使换浏览器或者清除缓存,内容也不会丢失。
注意:虽然浏览器存储大部分时候都比较可靠,但为了您的数据安全,在联网后,请务必及时发表或者保存到服务器草稿箱。
浏览器兼容
- 目前,本编辑器对Chrome浏览器支持最为完整。建议大家使用较新版本的Chrome。
- IE9以下不支持
- IE9,10,11存在以下问题
- 不支持离线功能
- IE9不支持文件导入导出
- IE10不支持拖拽文件导入
- 这里是 脚注 的 内容. ↩