Activity
1. 说下 Activity 的生命周期?
参考回答:
在 Activity 的生命周期涉及到七大方法,分别是:
onCreate() 表示 Activity 正在创建,常做初始化工作,如 setContentView 界面资源、初始化数据
onStart() 表示 Activity 正在启动,这时 Activity 可见但不在前台,无法和用户交互
onResume() 表示 Activity 获得焦点,此时 Activity 可见且在前台并开始活动
onPause() 表示 Activity 正在停止,可做 数据存储、停止动画等操作
onStop() 表示 Activity 即将停止,可做稍微重量级回收工作,如取消网络连接、注销广播接收器等
onDestroy() 表示 Activity 即将销毁,常做回收工作、资源释放
另外,当 Activity 由后台切换到前台,由不可见到可见时会调用 onRestart(),表示 Activity 重新启动
2. 说下 Activity 的四种启动模式?
参考回答:
standard 标准模式:每次启动一个 Activity 就会创建一个新的实例
singleTop 栈顶复用模式:如果新 Activity 已经位于任务栈的栈顶,就不会重新创建,并回调
onNewIntent(intent) 方法
singleTask 栈内复用模式:只要该 Activity 在一个任务栈中存在,都不会重新创建,并回调
onNewIntent(intent) 方法。如果不存在,系统会先寻找是否存在需要的栈,如果不存在该栈,就创建一个任务栈,并把该 Activity 放进去;如果存在,就会创建到已经存在的栈中
singleInstance 单实例模式:具有此模式的Activity只能单独位于一个任务栈中,且此任务栈中只有唯一一个实例
3. onStart()和onResume()/onPause()和onStop()的区别?
参考回答:
onStart() 与 onStop() 是从 Activity 是否可见这个角度调用的,onResume() 和 onPause()是从 Activity 是否显示在前台这个角度来回调的,在实际使用没其他明显区别。
4. Activity A启动另一个Activity B会回调哪些方法?如果Activity B是完全透明呢?如果启动的是一个Dialog呢?
参考回答:
Activity A 启动另一个 Activity B 会回调的方法:Activity A 的 onPause() --> Activity B 的onCreate()-->onStart()-->onResume()-->Activity A的 onStop();如果Activity B是完全透明的,则最后不会调用 Activity A 的 onStop();如果是对话框 Activity,同后种情况。
5. 谈谈onSaveInstanceState()方法?何时会调用?
参考回答:
当非人为终止 Activity 时,比如系统配置发生改变时导致 Activity 被杀死并重新创建、资源内存不足导致低优先级的 Activity 被杀死,会调用 onSavaInstanceState() 来保存状态。该方法调用在 onStop 之前,但和 onPause 没有时序关系。
6. onSaveInstanceState()与onPause()的区别?
参考回答:
onSaveInstanceState() 适用于对临时性状态的保存,而 onPause() 适用于对数据的持久化保存。
7. 如何避免配置改变时 Activity 重建?
参考回答:
为了避免由于配置改变导致 Activity 重建,可在 AndroidManifest.xml 中对应的 Activity 中设置android:configChanges="orientation|screenSize"。此时再次旋转屏幕时,该 Activity 不会被系统杀死和重建,只会调用 onConfigurationChanged 。因此,当配置程序需要响应配置改变,指定 configChanges 属性,重写 onConfigurationChanged 方法即可。
8. 优先级低的 Activity 在内存不足被回收后怎样做可以恢复到销毁前状态?
参考回答:
优先级低的 Activity 在内存不足被回收后重新打开会引发 Activity 重建。Activity 被重新创建时会调用 onRestoreInstanceState(该方法在onStart之后),并将 onSavaInstanceState 保存的 Bundle 对象作为参数传到onRestoreInstanceState与onCreate方法。因此可通过onRestoreInstanceState(Bundle savedInstanceState)和onCreate((Bundle savedInstanceState)来判断 Activity 是否被重建,并取出数据进行恢复。但需要注意的是,在onCreate取出数据时一定要先判断 savedInstanceState 是否为空。另外,谷歌更推荐使用 onRestoreInstanceState 进行数据恢复。
9. 谈谈singleTop和singleTask的区别以及应用场景?
参考回答:
singleTop 和 singleTask 的大致区别有:
singleTop:同个 Activity 实例在栈中可以有多个,即可能重复创建;该模式的 Activity 会默认进入启动它所属的任务栈,即不会引起任务栈的变更;为防止快速点击时多次 startActivity,可以将目标 Activity 设置为 singleTop
singleTask:同个 Activity 实例在栈中只有一个,即不存在重复创建;可通过 android:taskAffinity 设定该 Activity 需要的任务栈,即可能会引起任务栈的变更;常用于主页和登陆页
10. onNewIntent()调用时机?
参考回答:
启动模式为 singleTop 或 singleTask 的 Activity 在以下情况会回调 onNewIntent():
singleTop:如果新 Activity 已经位于任务栈的栈顶,就不会重新创建,并回调 onNewIntent(intent) 方法
singleTask:只要该 Activity 在一个任务栈中存在,都不会重新创建,并回调 onNewIntent(intent) 方法
11. 了解哪些Activity启动模式的标记位?
参考回答:
常见的两个标记为:
FLAG_ACTIVITY_SINGLE_TOP:对应singleTop启动模式
FLAG_ACTIVITY_NEW_TASK :对应singleTask模式
12. 如何启动其他应用的 Activity ?
参考回答:
在保证有权限访问的情况下,通过隐式 Intent 进行目标Activity的IntentFilter匹配,原则是:
一个 intent 只有同时匹配某个 Activity 的 intent-filter 中的 action、category、data才算完全匹配,才能启动该Activity。
一个Activity可以有多个 intent-filter,一个 intent只要成功匹配任意一组 intent-filter,就可以启动该Activity。
13. Activity 的启动过程?
参考回答:
调用 startActivity() 后经过重重方法会转移到 ActivityManagerService 的 startActivity(),并通过一个 IPC 回到 ActivityThread 的内部类 ApplicationThread 中,并调用其scheduleLaunchActivity()将启动Activity的消息发送并交由Handler H处理。Handler H对消息的处理会调用handleLaunchActivity()->performLaunchActivity()得以完成Activity对象的创建和启动。
Fragment
14. 谈一谈 Fragment 的生命周期?
参考回答:
Fragment 从创建到销毁整个生命周期中涉及到的方法依次为:onAttach()->onCreate()-> onCreateView()->onActivityCreated()->onStart()->onResume()->onPause()->onStop()->onDestroyView()->onDestroy()->onDetach(),其中和Activity有不少名称相同作用相似的方法,而不同的方法有:
onAttach():当Fragment和Activity建立关联时调用
onCreateView():当Fragment创建视图时调用
onActivityCreated():当与Fragment相关联的Activity完成onCreate()之后调用
onDestroyView():在Fragment中的布局被移除时调用
onDetach():当Fragment和Activity解除关联时调用
15. Activity和Fragment的异同?
参考回答:
Activity 和 Fragment 的相似点在于,它们都可包含布局、可有自己的生命周期,Fragment 可看似迷你活动。
不同点是,由于 Fragment 是依附在 Activity 上的,多了些和宿主Activity相关的生命周期方法,如onAttach()、onActivityCreated()、onDetach();另外,Fragment的生命周期方法是由宿主Activity而不是操作系统调用的,Activity中生命周期方法都是protected,而Fragment都是public,也能印证了这一点,因为Activity需要调用Fragment那些方法并管理它。
16. Activity 和 Fragment 的关系?
参考回答:
正如 Fragment 的名字“碎片”,它的出现是为了解决 Android 碎片化 ,它可作为Activity界面的组成部分,可在Activity运行中实现动态地加入、移除和交换。
一个 Activity中可同时出现多个Fragment,一个Fragment也可在多个Activity中使用。
另外,Activity的FragmentManager负责调用队列中Fragment的生命周期方法,只要Fragment的状态与Activity的状态保持了同步,宿主Activity的FragmentManager便会继续调用其他生命周期方法以继续保持Fragment与Activity的状态一致。
17. 何时会考虑使用Fragment?
参考回答:
非常经典的例子,即用两个Fragment封装两个界面模块,这样只使一套代码就能适配两种设备,达到两种界面效果;单一场景切换时使用Fragment更轻量化,如ViewPager和Fragment搭配使用
Service
18. 谈一谈Service的生命周期?
参考回答:在Service的生命周期涉及到六大方法,分别是:
onCreate():服务第一次被创建时调用
onStartComand():服务启动时调用
onBind():服务被绑定时调用
onUnBind():服务被解绑时调用
onDestroy():服务停止时调用
19. Service的两种启动方式?区别在哪?
参考回答:
第一种,其他组件调用Context的 startService() 方法可以启动一个Service,并回调服务中的onStartCommand()。如果该服务之前还没创建,那么回调的顺序是onCreate()->onStartCommand()。服务启动了之后会一直保持运行状态,直到 stopService() 或 stopSelf() 方法被调用,服务停止并回调onDestroy()。另外,无论调用多少次startService()方法,只需调用一次stopService()或stopSelf()方法,服务就会停止了。
第二种,其它组件调用Context的 bindService() 可以绑定一个Service,并回调服务中的onBind()方法。类似地,如果该服务之前还没创建,那么回调的顺序是onCreate()->onBind()。之后,调用方可以获取到onBind()方法里返回的IBinder对象的实例,从而实现和服务进行通信。只要调用方和服务之间的连接没有断开,服务就会一直保持运行状态,直到调用了 unbindService() 方法服务会停止,回调顺序onUnBind()->onDestroy()。
20. 一个Activty先start一个Service后,再bind时会回调什么方法?此时如何做才能回调Service的destory()方法?
参考回答:
startService()启动Service之后,再bindService()绑定,此时只会回调onBind()方法;若想回调Service的destory()方法,需要同时调用 stopService()和 unbindService()方法才能让服务销毁掉。
21. Service如何和Activity进行通信?
参考回答:
- 通过bindService()可以实现Activity调用Service中的方法,
- 通过广播实现Service向Activity发送消息
22. 用过哪些系统Service?
参考回答:
常用系统服务
23. 是否能在Service进行耗时操作?如果非要可以怎么做?
参考回答:
Service默认并不会运行在子线程中,也不运行在一个独立的进程中,它同样执行在主线程中(UI线程)。换句话说,不要在Service里执行耗时操作,除非手动打开一个子线程,否则有可能出现主线程被阻塞(ANR)的情况。
24. AlarmManager能实现定时的原理?
参考回答:
通过调用 AlarmManager 的 set() 方法就可以设置一个定时任务,并提供三个参数(工作类型,定时任务触发的时间,PendingIntent对象)。其中第三个PendingIntent对象是关键,一般会调用它的 getBroadcast() 方法来获取一个能够执行广播的PendingIntent。这样当定时任务被触发的时候,广播接收器的onReceive()方法就可以得到执行。即通过服务和广播的循环触发实现定时服务。
25. 前台服务是什么?和普通服务的不同?如何去开启一个前台服务?
参考回答:
和一般运行在后台的服务不同,前台服务的服务状态可以被用户一眼看到。它和普通服务最大的区别是,前者会一直有一个正在运行的图标在系统的状态栏显示,下拉状态栏后可以看到更加详细的信息,非常类似于通知的效果,且当系统内存不足服务被杀死时,通知会被移除。实现一个前台服务也非常简单,和发送一个通知非常类似,只不过在构建好一个Notification之后,不需要NotificationManager将通知显示出来,而是调用了 startForeground() 方法。
26. 是否了解ActivityManagerService,谈谈它发挥什么作用?
参考回答:
ActivityManagerService是Android中最核心的服务 , 主要负责系统中四大组件的启动、切换、调度及应用进程的管理和调度等工作,其职责与操作系统中的进程管理和调度模块类似。
27. 如何保证Service不被杀死?
参考回答:
可以采取以下几种解决方法:
在 Service 的onStartCommand()中设置flages值为START_STICKY,使得Service被杀死后尝试再次启动Service
提升Service优先级,比如设置为一个前台服务
在Activity的onDestroy()通过发送广播,并在广播接收器的onReceive()中启动Service
Broadcast Receiver
28. 广播有几种形式?什么特点?
参考回答:
普通广播:一种完全异步执行的广播,在广播发出之后,所有的广播接收器几乎都会在同一时刻接收到这条广播消息,因此它们接收的先后是随机的。
有序广播:一种同步执行的广播,在广播发出之后,同一时刻只会有一个广播接收器能够收到这条广播消息,当这个广播接收器中的逻辑执行完毕后,广播才会继续传递,所以此时的广播接收器是有先后顺序的,且优先级(priority)高的广播接收器会先收到广播消息。有序广播可以被接收器截断使得后面的接收器无法收到它。
本地广播:发出的广播只能够在应用程序的内部进行传递,并且广播接收器也只能接收本应用程序发出的广播。
粘性广播:这种广播会一直滞留,当有匹配该广播的接收器被注册后,该接收器就会收到此条广播。
29. 广播的两种注册形式?区别在哪?
参考回答:
广播的注册有两种方法:一种在活动里通过代码动态注册,另一种在配置文件里静态注册。两种方式的相同点是都完成了对接收器以及它能接收的广播值这两个值的定义;
不同点是动态注册的接收器必须要在程序启动之后才能接收到广播,而静态注册的接收器即便程序未启动也能接收到广播,比如想接收到手机开机完成后系统发出的广播就只能用静态注册了。
ContentProvider
30. ContentProvider了解多少?
参考回答:
作为四大组件之一,ContentProvider主要负责存储和共享数据。与文件存储、SharedPreferences存储、SQLite数据库存储这几种数据存储方法不同的是,后者保存下的数据只能被该应用程序使用,而前者可以让不同应用程序之间进行数据共享,它还可以选择只对哪一部分数据进行共享,从而保证程序中的隐私数据不会有泄漏风险。