一、handler机制是什么
Android中的消息通信机制,用于子线程与主线程间的通信,也能实现子线程间的通信。
这是一种非堵塞的消息传递机制,把子线程中的 UI更新信息发送给主线程(UI线程),以此完成UI更新操作。Android中主线程不能进行耗时操作,因此所有的耗时操作都需要在子线程中进行,而耗时操作完成后如果需要更新ui,就需要把信息传给主线程更新ui。
- 作用:为了多线程并发ui更新的同时保证线程安全
二、handler机制中重要的四个类
- Handler:发送和处理消息。发送:sendMessage();处理:handlerMessage()
- Message:Handler接收和处理的消息对象。用于不同线程间交换的数据
- MessageQueue:消息队列,用于存放所有通过handler发送的消息,等待被处理
- Looper:管理MessageQueue,调用loop()后进入无限循环,每当发现MessageQueue存在消息,即取出传递到handlerMessage()进行处理
三、工作原理
- 子线程:调用handler.sendMessage()发送消息 --> 调用handler.enqueueMessage()将消息放入 --> MessageQueue.enqueueMessage() 加入消息
- 主线程:程序启动时,默认通过Looper.loop()开启一个轮询,不断遍历消息队列,分发消息后处理消息
- 在ActivityThread.java的main函数中有准备Looper的函数和开启轮询的函数
-
Activity.main()-->Looper.loop() --> MessageQueue.next() --> handler.dispatchMessage --> handler.handleMessage()
四、handler机制中常见问题
1.子线程主线程创建handler的区别
- 主线程在进程启动时handler环境就创建好了,直接new;而子线程多了Looper.prepare()和Looper.loop()方法,相当于给handler准备looper
- 主线程的looper创建完不能退出,子线程可以
2.一个线程中能有几个handler,几个looper,几个messageQueue?
- 多个handler,一个looper,一个messageQueue
- 一个looper原因:
- Looper的构造方法是private私有方法,外部没法new一个Looper
- Looper类中有个静态变量static final ThreadLoad,只在运行初始化一次,所以只有一个,初始化方法Looper.prepare()
- 一个messageQueue:一个Looper维护一个messageQueue所以只有一个
3.为什么引发内存泄漏及解决方案?
- 原因:子线程进行延时操作期间Activity就被destory了,子线程持有的主线程的handler对象没被垃圾回收,就会泄露Activity
- 解决:1.handler定义成静态的内部类(就不能持有外部类),在内部持有Activity的弱引用 2.在onDestory()调用removeCallAndMessage(null)及时移除信息