android handlerthread 线程管理,Android线程之HandlerThread

HandlerThread是Android中一种特殊的线程,它内置了Looper,允许在子线程中创建Handler进行消息处理,避免了对UI线程的干扰。通过start()方法启动线程,getLooper()获取Looper,然后创建与之关联的Handler。文章详细分析了HandlerThread的run()方法和getLooper()方法的源码,展示了如何在主线程中创建并使用HandlerThread。使用HandlerThread可以方便地进行线程间通信和任务调度,同时提供了quit()和quitSafely()方法来退出消息循环,停止任务执行。

概述

HandlerThread是Thread的一个子类,是Android中提供的另一种线程形态。

Handy class for starting a new thread that has a looper. The looper can then be

used to create handler classes. Note that start() must still be called.

这个是官方类的说明。说这个类是一个带有Looper的线程,这个looper用来创建handler使用的。切记要调用start()方法来启动。

我擦,有线程、有looper这不正是我们当初声称在子线程中构建handler消息系统的所需要的吗?

源码分析

看一下这个线程核心run()方法源码:

@Override

public void run() {

mTid = Process.myTid(); //获得线程的id

Looper.prepare();

synchronized (this) { // 之所以用同步代码块,是处理getLooper() 的同步问题,保证looper的获得。

mLooper = Looper.myLooper();

notifyAll(); //获取完毕后,通知getLooper()

}

Process.setThreadPriority(mPriority); //设置线程的优先级

onLooperPrepared();

Looper.loop();

mTid = -1;

}

Looper.prepare()创建Looper及MessageQueue

然后调用Looper.loop()是这个消息系统循环起来

onLooperPrepared() 这个方法是空方法体,子类可以重写这个方法,做些线程循环前的操作

再看一下getLooper()源码:

public Looper getLooper() {

if (!isAlive()) {

return null;

}

// If the thread has been started, wait until the looper has been created.

//如果线程活着但mLooper却是空的,则进入等待,等待mLooper被创建完毕

//这里的wait方法 与 run方法中的 notifyAll 实现了线程的同步

synchronized (this) {

while (isAlive() && mLooper == null) {

try {

wait();

} catch (InterruptedException e) {

}

}

}

return mLooper;

}

那很明显,这个HandlerThread的目的就是让我们创建一个Handler,然后所有的任务操作成功的转给了Handler来处理完成。

但注意的是这个Handler的消息处理是运行在子线程中的。

用法

在主线程中创建handler,简单的模拟一下HandlerThread工作原理

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

setContentView(R.layout.activity_main);

// 创建HandlerThread

HandlerThread handlerThread = new HandlerThread("handlerThread");

// 必须调用start()方法进而执行run方法体

handlerThread.start();

//获得这个线程的looper

Looper looper = handlerThread.getLooper();

//创建这个looper对应的Handler

handler = new Handler(looper) {

@Override

public void handleMessage(Message msg) {

Log.d("smart", "当前的线程:" + Thread.currentThread().getName());

if (msg.what == 2) {

Log.d("smart", "handleMessage: 收到了延迟消息 2");

}

}

};

Message message = Message.obtain();

message.what = 2;

handler.sendMessage(message);

}

442a022b286e

QQ截图20170519162157.png

由于这个handler回调是运行在子线程中的,因此如果你想要更新UI可以借助主线程的默认的looper来实现,这个问题又愉快的转化到了子线程更新UI的问题。

除此之外,HandlerThread还提供了方法来退出消息循环,停止任务的执行。

quit()

quitSafely()

总结

HandlerThread其本质就是一个线程,只不过这个线程加入了Handler消息异步处理的机制。

那这与普通的创建线程的好处是什么呢?

HandlerThread自带Looper使他可以通过消息来多次重复使用当前线程,节省开支;

android系统提供的Handler类内部的Looper默认绑定的是UI线程的消息队列,对于非UI线程又想使用消息机制,于是HandlerThread就被登场了,它不会干扰或阻塞UI线程;

在一个,线程有了消息队列的机制,那任务的控制顺序等都交给了优秀的Handler异步消息机制,有种托管的轻松。

Android中的IntentService中就使用了HanlderThread

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符  | 博主筛选后可见
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值