【Android FrameWork】综合面试问题
问题:性能差,把图片写到文件需要耗时,对方读取文件也需要耗时
通过 IPC 的方式转发图片数据
不经过文件系统,但是需要多次拷贝
IPC 方式传图
Binder:性能好,使用方便,但是大小有限制
Socket、管道:两次拷贝,也有大小限制
共享内存:性能不错
主要注意点
1.性能,减少拷贝次数
2.内存泄漏,资源及时关闭
TransactionTooLargeException
发出去的或者返回的数据量太大
Binder 缓存用于该进程所有正在进行中的 Binder 事务
进程弃用 binder 机制会映射一块内存,大小是 1M
跨进程通信申请的缓冲区大小是不能超过 1M 的
所有 binder 事务共享这 1M 内存空间,应该尽量避免同时跑多个事务,尤其是数据量很大的事务
大数据量打碎分批发,或按需发(官方建议)
总结?跨进程传递大图片的方式
图片写到文件,路径传到另一个进程,再读出来
intent 传图,但是容易抛异常,原因是什么
binder 调用传图,底层 ashmem 机制
2. ThreadLocal 原理
关于更多面试题资料,可以前往?GitHub?自行查阅。
考察点
ThreadLocal 的适用于什么场景?
ThreadLocal 的使用方式是怎样的?
ThreadLocal 的实现原理是怎样的?
ThreadLocal 在 FrameWork 中的使用
Looper
Choreorgapher
原理
每一个线程都有一张表,其实就是一个数组,key 和 value 都存储在数组中
key 存储在 weakReference 中,value 对应对象如 Looper、Choreorgapher 等
一个应用里可以定义多个 ThreadLocal,ThreadLocal 都有自己的哈希值,哈希值根据 hashCounter 计算
算出 hash 值之后,对表的 size 取余数,就能算出 key:value 在表中的 index 值
如果发生了 hash 冲突,就会从当前 index 开始向下遍历数组,放在空闲的位置上
代码如下:
总结
同一个 ThreadLocal 对象,在不同线程 get 返回不同 value
Thread 对象里有张表,保存 ThreadLocal 到 value 的映射关系
这张表是怎么实现的?(见上面的原理分析)
是如何解决 hash 冲突的?(见上面的原理分析)
3. 说说 Looper 的副业(待完善)
Looper 里可以监听其它描述符
创建管道,跨进程传数据,用 looper 监听描述符事件
4. 怎么检查线程有耗时任务
两种情况
正常的,轻微阻塞
不正常的,严重阻塞
检测机制
WatchDog:
Framework 自带,检查 system_server 中系统服务是否正常
用于检查死锁或者线程异常
BlockCanary
开源框架,用于检查线程是否有耗时任务
WatchDog?WatchDog 的作用上面说过:一是检查是否发生了死锁,二是检查线程是否被任务 blocked
WatchDog 是一个线程
看下 WatchDog 的关键变量:
mHandlerCheckers 是核心列表,添加了多个 HandlerChecker
每一个 Checker 都对应了一个线程,比如主线程、前台线程、IO 线程等,这几个线程都是 system_server 中非常重要的工作线程
每一个 HandlerChecker 下都有一个 Monitor 列表
addMonitor 实质上是向 mMonitorChecker 加了一个 BinderThreadMonitor,用于检测 binder 线程是否正常
看下下图
第一个 MonitorChecker 用户检查系统服务是否发生了死锁,在单独的线程中检查,
原理就是在另外的线程中去尝试拿到锁,拿到了就正常返回
如果一直拿不到,就可能是产生了死锁问题
如图 AMS 中代码细节
同时服务还会把自己的工作线程 new 一个 HandlerChecker,也注册到 watchDog,每一个 handlerChecker 都会对应一个线程,在线程中派发 handlerChecker
BlockCanary?原理就是通过 messageLogging 在消息分发前后的时间戳打印,利用时间戳的差算出消息执行耗时
5. 怎么同步处理消息
「同步处理消息」:我们发了一个消息到另外一个线程去处理,并没有直接返回,而是挂在那里等待消息处理完毕,有些时候还需要拿到消息处理结果,这就是同步处理消息
适用场景如图 124
应用要访问另一个进程的服务,请求会调到服务进程的 binder 线程池中,binder 线程切换到工作线程处理请求,工作线程工作的时候 binder 线程会一直等待,应用端也会一直等着,等到处理完成后返回结果给给应用
6. 你去了解 framework 是为了解决一个什么样的问题,怎么解决的?
考察点
你有没有解决复杂问题的经验
你有没有深入研究底层原理的习惯
你的知识体系是否有一定深度
7. 应用组件相关题目
为什么 Activity 在 onResume 之后才会显示出来
ActivityThread handleResumeActivity 时 WindowManager 才会 addView 并 makeVisible
bindService 的时候 Rebind 总是调不到,研究原理
TODO
广播 onReceive 的 context 可否启动 Activity, 显示 Dialog?
TODO
发现 provider 的 onCreate 比 Application 还早,研究一下
Application 构造方法 –> Application.attachBaseContext –> ContentProvider.onCreate –> Application.onCreate –> Activity.onCreate
看下 ActivityThread.java 的 handleBindApplication 方法:
图 130
8. 消息通信相关题目
intent 带的数据量大了会异常,研究原因
binder 机制 1m 限制
需要跨进程传大图,研究 Bitmap 传输原理,Ashmem 机制
想知道 Handler 消息延时的精度怎么样,去了解原理
延迟处理不是延迟发送,精度不太准确
为什么有时候 IdleHandler 调不到,去了解原理
主线程繁忙,一直在处理消息
比如:
在 View 的 onDraw 方法里面无限制的直接或者间接调用 View 的 invalidate 方法。
做一个无限轮询的 View 动画。
9.性能优化相关题目
ANR 了,看主线程是否有耗时任务
卡顿掉帧,了解屏幕刷新机制,研究 Choregrapher
启动速度优化,了解应用启动原理
内存优化,清理不必要的资源
10. Android FrameWork 用到了哪些设计模式?请举例说明
单例模式
Framework 中:SingleTon 类,应用 IAM
![](https://img-blog.csdnimg.cn/img_co
nvert/4d129d429226fa13cbca5b952b04fe9c.png)
线程内:
线程间/进程内:Choreographer,ThreadLocal 线程私有,不同线程获取不同的实例,同一线程获取同一实例
评论