HandlerThread
首先文档对这个类的介绍
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.
如果我有一个耗时的任务需要放在非 UI 线程处理,一般情况下是 new 出一个 thread 来执行,然而,这样就存在一个性能问题:多次创建和销毁线程是很耗系统资源的。
为了解这种问题,我们可以自己构建一个循环线程Looper Thread,当有耗时任务投放到该循环线程中时,线程执行耗时任务,执行完之后循环线程处于等待状态,直到下一个新的耗时任务被投放进来。这样一来就避免了多次创建Thread线程导致的性能问题了。其实 Android 系统已经为我们准备了 就是 HandlerThread
HandlerThread使用步骤
//创建实例对象
HandlerThread handlerThread = new HandlerThread("handlerThread");
//启动HandlerThread线程
handlerThread.start();
//构建循环消息处理机制
Handler subHandler = new Handler(handlerThread.getLooper(), new Handler.Callback() {
@Override
public boolean handleMessage(Message msg) {
//实现自己的消息处理
return true;
}
});
源码分析
public class HandlerThread extends Thread {
//优先级
int mPriority;
int mTid = -1;
//成员变量里有 Looper,在 run() 中初始化
Looper mLooper;
/**
* Constructs a HandlerThread.
* @param name
* @param priority The priority to run the thread at. The value supplied must be from
* {@link android.os.Process} and not from java.lang.Thread.
*/
public HandlerThread(String name, int priority) {
super(name);
mPriority = priority;
}
/**
* Call back method that can be explicitly overridden if needed to execute some
* setup before Looper loops.
*/
protected void onLooperPrepared() {
}
@Override
public void run() {
mTid = Process.myTid();
//初始化 looper
Looper.prepare();
synchronized (this) {
//初始化 mLooper
mLooper = Looper.myLooper();
notifyAll();
}
Process.setThreadPriority(mPriority);
onLooperPrepared();
//开始循环取消息执行的队列
Looper.loop();
mTid = -1;
}
此外还有一些其他的方法
quitSafely()
Looper getLooper()
举个栗子
Android 系统的 IntentService 就是使用了HandlerThread
在 onCreate 方法中
@Override
public void onCreate() {
// TODO: It would be nice to have an option to hold a partial wakelock
// during processing, and to have a static startService(Context, Intent)
// method that would launch the service & hand off a wakelock.
super.onCreate();
//新建了工作线程的HandlerThread
HandlerThread thread = new HandlerThread("IntentService[" + mName + "]");
thread.start();
mServiceLooper = thread.getLooper();
//由工作线程的HandlerThread 新建出的Handler,其工作队列是在HandlerThread中的线程
mServiceHandler = new ServiceHandler(mServiceLooper);
}
@Override
public void onStart(Intent intent, int startId) {
//与普通的 service 不同的是,我们希望在 service 中行耗时的任务,不想新建 thread 不方便管理。这里任然是主线程,只不过通过发送消息,将耗时的任务放在了 HandlerThread 中
Message msg = mServiceHandler.obtainMessage();
msg.arg1 = startId;
msg.obj = intent;
mServiceHandler.sendMessage(msg);
}
private final class ServiceHandler extends Handler {
public ServiceHandler(Looper looper) {
super(looper);
}
@Override
public void handleMessage(Message msg) {
//我们复写的onHandleIntent()将耗时的操作放在这里onHandleIntent()中
onHandleIntent((Intent)msg.obj);
stopSelf(msg.arg1);
}
}
//在 onDestory 时要销毁队列,不然会内存泄露
@Override
public void onDestroy() {
mServiceLooper.quit();
}