吐槽:子线程中创建Handler对象就很牛逼么?效率就很高么?使用起来就很方便么?

很多面试题问到“子线程中能否创建Handler?”。
之前一直使用HandlerThread框架,在主线程中创建与子线程关联的Handler实例,也没考虑过这个问题。

代码如下:

HandlerThread  mHandlerThread = new HandlerThread("Controller Message Processing Thread");
mHandlerThread.start();
Looper  mServiceLooper = mHandlerThread.getLooper();
Handler mMessageHandler = new Handler(mServiceLooper) {
        @Override
        public void handleMessage(Message msg) {

        }
 };

针对“子线程中能否创建 Handler实例?”基本上就是说直接new Handler()无参数实例,
看源码,使用无参构造函数时确实有抛出异常的可能:

public Handler() {
    this(null, false);
}
public Handler(Callback callback, boolean async) {
      mLooper = Looper.myLooper();
      if (mLooper == null) {
          throw new RuntimeException(
                "Can't create handler inside thread that has not called Looper.prepare()");
        }
}

结论:在创建Handler之前,必须在子线程中调用Looper.prepare(),否则就抛出异常。
总觉得这样的面试题有些傻x,考察点难道就是如上的结论?
可是完全也没必要非得在子线程中创建Handler实例啊,在主线程完全可以完成所有的事情,解决所有的问题,完全可以不去踩这个坑的,你踩过一次坑,别人必须也得踩过才是熟练使用,没踩过就就是大笨蛋?
得出结论:这类面试题说明你踩过的坑别人没踩过就是蠢货......

其实主要就是考察你对他们区别的理解。
http://www.cnblogs.com/xgjblog/p/5258947.html

主线程会默认创建一个Looper,所以在主线程中创建handler时,不会报错,
而子线程中没有默认创建Looper,所以在子线程中创建handler 时,会报错,提示需要调用Looper.prepare(),方法在子线程创建一个Looper
好好去理解handler Looper MessageQueue 的关系吧

可以参考一下我的博客 http://blog.csdn.net/ganyao939543405/article/details/52438180
完整解析了 Android 消息框架的源码,源码加了很多注解。
简单的说 普通 Thread 和 handlerThread 区别就是 HandlerThread

run() {
while(isOn) {
if () {
Runnable runnable = null;
if (runnable = hasMessage() //这里没有消息会阻塞) {
handlerThreadRun(runnable);
}
}
}

仅仅是封装了一下而已

你自己在普通线程里面 Looper.looer() 是一样的效果

handler的作用就是在子线程中更新主线程UI,如果你只会在主线程中创建handler用处大吗?特殊情况下比如只给子线程你,让你直接post一个接口更新主线程,你怎么办?
这个时候你只能:mHandler = new Handler(Looper.getMainLooper()). post (new Runnable()) {
//update UI