标签:
相比于AsyncTask,HandlerThread更好操控一些,因为当需要中断异步操作的时候例如:退出activity,屏幕旋转等等,虽然AsyncTask提供了中断的方法cancle( );有时候会失效,
从源码可以看出,它调用的是interrupt( )方法,有必要说一下java中的中断机制,Java中断机制是一种协作机制,也就是说通过中断并不能直接终止另一个线程,而需要被中断的线程自己处理中断。当调用interrupt()方法的时候,只是设置了要中断线程的中断状态。既然不能直接中断线程,那只好通过暴力方式中断了。
HandlerThread的使用
HandlerThread handlerThread = new HandlerThread("your tag"); handlerThread.start(); Looper looper = handlerThread.getLooper(); Handler handler=new Handler(looper); { @Override public void handleMessage(Message msg) { if (msg.what == 0) { //可执行耗时操作 } } } handler.sendEmptyMessage(0);
以上是使用HandlerThread的步骤,先创建HandlerThread对象,执行,再获取looper对象,创建Handler对象,传入looper,在handler里面重写handleMessage方法,里面可执行耗时操作,最后记得让handler发送message,根据message里面的字段来执行handleMessage方法相应的代码块。
下面是我实际开发中遇到的问题,大概功能是开一个子线程,读取所有联系人的电话号码,然后把结果到一个list中。
handlerThread = new HandlerThread("getContents"); mHandler = new Handler() { @Override public void handleMessage(Message msg) { // TODO Auto-generated method stub changeData(phoneNumList); } }; handlerThread.start(); Looper looper = handlerThread.getLooper(); final Handler mHandler1 = new Handler(looper) { @Override public void handleMessage(Message msg) { if (msg.what == UPDATE) { GetContentsUtil.init(mContext); phoneNumList = GetContentsUtil.getPhoneNumList(); mHandler.sendEmptyMessage(0); } } }; mHandler1.sendEmptyMessage(UPDATE);
其中这里的handlerThread和mHandler对象是activity私有的
这里为什么会有两个Handler呢?首先第一个mHandler1对应的域是子线程,执行耗时操作,获取数据之后你要更新啊,但是安卓里面只能在UI线程里面更新数据啊,很简单,再创建一个mHandler(mHandler是activity私有的,对应的域自然是UI线程),发送一个信号给它,然后更新UI的代码放在这个就可以了。
之前说到HandlerThread暴力中断,现在回归正题,
@Override protected void onDestroy() { // TODO Auto-generated method stub super.onDestroy(); // 销毁acitivity时销毁子线程 try { handlerThread.getLooper().quit(); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); } handlerThread = null; }
在activity销毁的时候调用,
直接把looper给干掉。中断当前处理的操作,后续任何发送到消息队列的消息都无效。
标签:
原文地址:http://my.oschina.net/carbenson/blog/523257