一些我所知我所用的笔记-----《Handler篇》

        已经有很久很久没有更新日志啦,没办法,人的惰性嘛,想想自己在这一行整整一年多了,学到的都是一些零散的知识点,一个完整的项目经验还没有,说来惭愧...好啦,废话不多说了,最近有好好的研究了一下Android中的Handler一些用法,在这里记录一下,一来是给自己加深印象,再者就是所谓的分享精神,这里所介绍的并不涉及很深的层次,就是一些细节上解释以及代码示例,那么接下来进入正题吧.....

       一.Handler的基本使用

            一般我们使用Handler的场景:在某个条件下,在主线程中通过发送一个信号,然后在子线程执行相应的逻辑,然后将处理完后的结果返回给主线程并更新相应的UI之类的(这是比较主要的),那我们来写个示例吧:

<span style="font-size:18px;">public class MainActivity extends Activity {

	private Handler mMainHandler = new Handler(){

		@Override
		public void handleMessage(Message msg) {
			super.handleMessage(msg);
			switch (msg.what) {
			case 1:
				Log.e("tag", "MainHandler in the " + Thread.currentThread().getName());
				String str = (String) msg.obj;
				Log.e("tag","Message from  " + str);
				break;
			default:
				break;
			}
		}
		
	};
	
	
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		
		MyThread myThread = new MyThread();
		myThread.start();
		
	}

	
	class MyThread extends Thread{

		@Override
		public void run() {
			
			Message msg  = mMainHandler.obtainMessage();
			msg.what = 1;
			msg.obj = "I am from " + Thread.currentThread().getName();
			mMainHandler.sendMessage(msg);
			
		}
		
	}
}</span>
      这里新建子线程并调用Handler.sendMessage()方法向主线程发送消息,这里可以通过打印日志可以看出,这是一个线程中的通信。

      因为java语言独特的传址特性,主要在相应的地方,将Handler作为参数传入方法内,就可以进行通信啦。

    

     二.如何在子线程中使用Handler

     这里小伙伴就说了,子线程使用hanler不就是在子线程new Handler()么?其实不完全是这样的,这里有个知识点来普及下,每个线程中有且只有一个Looper对象,并且每个Looper对象维护一个消息队列,但是若两个Handler创建时使用同一个Looper对象,是不是就可以共用handMessage()方法呢,那么,我可以负责人的告诉你,并不是这么理解的,那么进入主题,如何在子线程中使用Handler呢,那么看下示例代码:

<span style="font-size:18px;">class MyThread extends Thread{

		@Override
		public void run() {
			Looper.prepare();
			
			Looper looper = Looper.myLooper();
			Handler firstHandler = new Handler(looper){

				@Override
				public void handleMessage(Message msg) {
					super.handleMessage(msg);
					switch (msg.what) {
					case 1:
						Log.e("tag", "From first handler");
						break;
					default:
						break;
					}
				}
			};
			
			Handler secondHandler = new Handler(looper);
			firstHandler.sendEmptyMessage(1);
			looper.loop();
			}
	}</span>

    那有的小伙伴又会有疑问,在主线程中没有调用Looper.prepare()呢,那么根据源码,主线程会自动调用 Looper.prepare();


    三.Handler中的Post()方法使用

    在Handler.post()方法中,其中传入的参数为runnable对象,那么根据runnable的特性,其并不是创建子线程并执行相关的逻辑,而是根据runnable创建的所在线程所决定的,那么由此得来,由主线程创建的Handler对象,调用post方法时,则在主线程中执行相应的逻辑(可以更新UI界面),那么示例代码如下:

MyRunnable r = new MyRunnable();
		Handler handler = new Handler();
		handler.post(r);

class MyRunnable implements Runnable{
		@Override
		public void run() {
			Log.e("TAG", "OnRunning"+Thread.currentThread().getName());
		}
	}

    四.HandlerThread的使用方法
    照例,先简单的介绍一下HandlerThread,由HandlerThread中获取的Looper对象生成的Handler,通过sendMessage()方法时,其handleMessage()方法是在子线程中执行的,那么我们继续来看一下示例代码:

protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		
		HandlerThread mHandlerThread = new HandlerThread("TestHandlerThread");
		mHandlerThread.start();
		
		Looper looper = mHandlerThread.getLooper();
		
		Handler handler = new Handler(looper){

			@Override
			public void handleMessage(Message msg) {
				super.handleMessage(msg);
				switch (msg.what) {
				case 1:
					Log.e("tag", "HandlerThread -->"+Thread.currentThread().getName());
					break;

				default:
					break;
				}
			}
		};
		
		handler.sendEmptyMessage(1);
	}

最后,介绍一个小小的优化方法,一般我们生成一个Message对象时,是直接new的,然后各种赋值,当然这不算比较好的方法,那么,通过handler.obtainMessage()方法来生成一个messsage对象比较好,为什么呢?留给大家看源码咯~

如果文中还有什么补充或者是不严谨的地方,还望指出哦 ~谢谢




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值