首先,我不喜欢的在Android项目中用的Handler是长这样的
private static final int DO_SOMEGTING = 1; private static final int DO_OTHER_THING = 2; private Handler mHandler = new Handler() { @Override public void handleMessage(Message msg) { super.handleMessage(msg); switch (msg.what) { case DO_SOMEGTING: xxxxxxxxxxx 具体代码 xxxxxxxx break; case DO_OTHER_THING: xxxxxxxxxxx 具体代码 xxxxxxxx break; } }
这种写法的主要原因,我想,绝大多数是因为在非UI线程中做了一些操作,比如网络请求,之后需要对界面进行操作,这时候操作就需要在UI线程中进行了。例如下面这样发送一个消息给Handler
Message msg = new Message(); msg.what = DO_SOMEGTING; msg.obj = result; mHandler.sendMessage(msg);
上面这样的写法在各种第三方库或者博客上面随处可见,但是,为什么我不喜欢在实际项目中使用这样的写法呢?
1. 这样会造成代码混乱,降低代码的可读性
写代码其实就跟你高考的时候写作文一样,不仅要表达出你的意思,还要让阅卷老师一眼就看得懂你在写什么,结构要清晰,因为代码不仅仅是写给你自己看的,还要给团队其他人看的,或者某一天你晚上12点在公司加班,吃着泡面,吃着吃着突然就挂了(-_-#),或者你突然双色球中了一等奖把奖池掏空了,潇潇洒洒跟Boss say goodbye,这时候,后面接手你代码的哥们(或者妹子)看到你一个Handler里面好几百行,switch里面n个case,心中该是有多奔腾。就算你福如东海寿比南山运气背到爆5块钱都没中过,但当你像上面那样sendMessage(msg)
之后,我想,就算是你自己写的代码,还是要去全局搜索sendMessage之后会去执行哪里的代码,话说这跟你用goto是不是有异曲同工之妙!!!!
2.有更优雅的实现方法
现在RxAndroid都已经发布到1.1版本了,已经是稳定版了,所以很多开发者也在项目中使用RxAndroid,不得不说,流式的编程方式用起来很爽,就像下面这样
Observable.create((Observable.OnSubscribe<String>) subscriber -> { //这是在io线程执行的 }) .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) .subscribe( result->{//这是在UI线程执行的} );
这里顺便说下,很多人弄不清楚subscribeOn和observeOn对应的是执行哪一部分的代码,subscribeOn 执行的是subscriber的代码,observeOn执行的是subscribe的代码,这个要是搞不清楚,自己写个小例子测试下很容易就知道了。
什么时候可以使用Handler
1.写提供给别人用的第三方库的时候
当你在写一个库的时候,就应该尽量避免引入其他第三方库,因为没准你的库就那么几十一百K,然后你引用的库好几M,这时候就要重新思考整个库的设计了,例如提供另外可选的库来给用户选择,例如retrofit的json转换就提供了几个版本的可选库。
2.写博客的时候
很多时候写博客就专门是为了针对某个知识点进行讲解,这个时候引入一大堆的第三方库是很麻烦的,还要额外多讲解引入的库,所以很多博客在写的时候用Handler是因为这个不用去特意讲解和引入其他库,让读者关注点集中在讲解的知识点上。
#不想引用第三方库应该怎么做
很多人又不想引用第三方库又想让代码看起来简洁易懂,这时候就要想办法了,比如将需要在UI线程执行的代码块封装成方法,这样不仅在看代码的时候直接点击进入方法还可以提高代码的复用性。然后在需要执行方法的地方调用
handler.post(new Runnable(xxx()));//这里xxx()就是封装好的方法
{(-_-)}那些说handler.post(Runnable)这样是post一个线程的,我就原谅下你的无知,感觉点进去看下具体实现吧!!!!!