1. Android中进程和线程的关系,区别
-
进程是什么? 它是系统进行资源分配和调度的一个独立单位,也就是说进程是可以独立运行的一段程序。
-
线程又是什么? 线程进程的一个实体,是CPU调度和分派的基本单位,他是比进程更小的能独立运行的基本单位,线程自 己基本上不拥有系统资源。在运行时,只是暂用一些计数器、寄存器和栈 。
区别:
- 进程有不同的代码和数据空间,而多个线程则共享数据空间,每个线程有自己的执行堆栈和程序计数 器为其执行上下文。
- 进程间相互独立,同一进程的各线程间共享。
- 进程间通信IPC,线程间可以直接读写进程数据段(如全局变量)来进行通信——需要进程同步和互 斥手段的辅助,以保证数据的一致性。
2. 为何需要进行IPC,多进程通信可能会出现什么问题
为了保证进程空间不被其他进程破坏或干扰,Linux中的进程是相互独立或相互隔离的。在Android系统 中一个应用默认只有一个进程,每个进程都有自己独立的资源和内存空间,其它进程不能任意访问当前 进程的内存和资源。这样导致在不同进程的四大组件没法进行通信,线程间没法做同步,静态变量和单 例也会失效。所以需要有一套IPC机制来解决进程间通信、数据传输的问题。
开启多进程虽简单,但会引发如下问题,必须引起注意:
- 静态成员和单例模式失效
- 线程同步机制失效
- SharedPreferences 可靠性降低
- Application 被多次创建
对于前两个问题,可以这么理解,在Android中,系统会为每个应用或进程分配独立的虚拟机,不同的 虚拟机自然占有不同的内存地址空间,所以同一个类的对象会产生不同的副本,导致共享数据失败,必 然也不能实现线程的同步。
由于 SharedPreferences 底层采用读写XML的文件的方式实现,多进程并发的读写很可能导致数据异常。 Application 被多次创建和前两个问题类似,系统在分配多个虚拟机时相当于把同一个应用重新启动多次,必然会导致 Application 多次被创建,为了防止在 Application 中出现无用的重复初始化,可使用进程名来做过滤,只让指定进程的才进行全局初始:
public class MyApplication extends Application{
@Override
public void onCreate() {
super.onCreate();
String processName = "com.shh.ipctest";
if (getPackageName().equals(processName)){
// do some init
}
}
}
3. Android中IPC方式有几种、各种方式优缺点
进程间通信方式对比:
4. 为何新增Binder来作为主要的IPC方式
Android 也是基于 Linux 内核,Linux 现有的进程通信手段有管道/消息队列/共享内存/套接字/信号量。 既然有现有的IPC方式,为什么重新设计一套 Binder 机制呢?
主要是出于以上三个方面的考量:
-
效率:传输效率主要影响因素是内存拷贝的次数,拷贝次数越少,传输速率越高。从Android进程架 构角度分析:对于消息队列、Socket和管道来说,数据先从发送方的缓存区拷贝到内核开辟的缓存区 中,再从内核缓存区拷贝到接收方的缓存区,一共两次拷贝。 一次数据传递需要经历:用户空间 –> 内核缓存区 –> 用户空间,需要2次数据拷贝,这样效率不高。 而对于Binder来说,数据从发送方的缓存区拷贝到内核的缓存区,而接收方的缓存区与内核的缓存区是 映射到同一块物理地址的,节省了一次数据拷贝的过程 : 共享内存不需要拷贝,Binder的性能仅次于共 享内存。
-
稳定性:上面说到共享内存的性能优于Binder,那为什么不采用共享内存呢,因为共享内存需要处 理并发同步问题,容易出现死锁和资源竞争,稳定性较差。 Binder基于C/S架构 ,Server端与Client端 相对独立,稳定性较好。
-
安全性:传统Linux IPC的接收方无法获得对方进程可靠的UID/PID,从而无法鉴别对方身份;而 Binder机制为每个进程分配了UID/PID,且在Binder通信时会根据UID/PID进行有效性检测。
5. 什么是Binder
-
从进程间通信的角度看,Binder 是一种进程间通信的机制;
-
从 Server 进程的角度看,Binder 指的是 Server 中的 Binder 实体对象(Binder类 IBinder);
-
从 Client 进程的角度看,Binder 指的是对 Binder 代理对象,是 Binder 实体对象的一个远程代理
-
从传输过程的角度看,Binder 是一个可以跨进程传输的对象;Binder 驱动会自动完成代理对象和本地 对象之间的转换。
-
从Android Framework角度来说,Binder是ServiceManager连接各种Manager和相应ManagerService 的桥梁 Binder跨进程通信机制:基于C/S架构,由Client、Server、ServerManager和Binder驱动组 成。
进程空间分为用户空间和内核空间。用户空间不可以进行数据交互;内核空间可以进行数据交互,所有 进程共用一个内核空间
Client、Server、ServiceManager均在用户空间中实现,而Binder驱动程序则是在内核空间中实现的;
6. Binder的原理,Binder Driver 如何在内核空间中做到一次拷贝的?
7. 使用Binder进行数据传输的具体过程
8. Binder框架中ServiceManager的作用
9. 什么是AIDL
10. AIDL使用的步骤
11. AIDL支持哪些数据类型
12. AIDL的关键类,方法和工作流程
13. 如何优化多模块都使用AIDL的情况
14. 使用 Binder 传输数据的最大限制是多少,被占满后会导致什么问题
15. Binder 驱动加载过程中有哪些重要的步骤
16. 系统服务与bindService启动的服务的区别
17. Activity的bindService流程
18. 不通过AIDL,手动编码来实现Binder的通信
Android高级面试题及答案解析
需要《Android高级面试题及答案解析》可以点击此处免费领取!