文章来源:http://blog.csdn.net/wyzxk888/article/details/6968848

推荐文章:http://blog.csdn.net/yegongheng/article/details/38845953

花了若干天反复的学习了一下Handler,但是还是留下了许多问题,可能是自己太笨了,这里也自己留两份笔记方便以后回头看。

Handler注意点1:在哪个线程创建的Handler,Handler就属于哪个线程。

Handler注意点2:Handler调用Post(Runnable)函数时,不会启动另外一个线程,就是当前线程。

这个在做UI更新中要特别注意,这也是很多人问为什么调用了post方法UI线程还是阻塞了的原因,因为这样只是用Handler实现了异步,没有多线程。

Handler注意点3:在子线程中默认是没有MessageQueue的。

解决方法:用主线程的Handler发送消息到主线程的MessageQueue。

子线程创建Handler,获取主线程的MessageQueue,即获得主线程的Looper,(方法new Handler(Loop.getMainLooper()))


单纯异步与多线程异步证明:

XML布局:

[html] view plain copy
  1. <?xmlversion="1.0"encoding="utf-8"?>
  2. <LinearLayoutxmlns:android="http://schemas.android.com/apk/res/android"
  3. android:layout_width="fill_parent"
  4. android:layout_height="fill_parent"
  5. android:orientation="vertical">
  6. <Button
  7. android:id="@+id/button1"
  8. android:layout_width="wrap_content"
  9. android:layout_height="wrap_content"
  10. android:text="handlertest1"/>
  11. <Button
  12. android:id="@+id/button2"
  13. android:layout_width="wrap_content"
  14. android:layout_height="wrap_content"
  15. android:text="handlertest2"/>
  16. <Button
  17. android:id="@+id/button3"
  18. android:layout_width="wrap_content"
  19. android:layout_height="wrap_content"
  20. android:text="handlertest3"/>
  21. <Button
  22. android:id="@+id/button4"
  23. android:layout_width="wrap_content"
  24. android:layout_height="wrap_content"
  25. android:text="handlertest4"/>
  26. <ProgressBar
  27. android:id="@+id/progressBar1"
  28. style="?android:attr/progressBarStyleHorizontal"
  29. android:layout_width="match_parent"
  30. android:layout_height="wrap_content"/>
  31. <TextView
  32. android:id="@+id/textView1"
  33. android:layout_width="wrap_content"
  34. android:layout_height="wrap_content"
  35. android:text="whichtest?:"
  36. android:textAppearance="?android:attr/textAppearanceLarge"/>
  37. </LinearLayout>


Java Code:

[java] view plain copy
  1. packagenet.john;
  2. importandroid.app.Activity;
  3. importandroid.os.Bundle;
  4. importandroid.os.Handler;
  5. importandroid.os.Message;
  6. importandroid.view.View;
  7. importandroid.widget.Button;
  8. importandroid.widget.ProgressBar;
  9. importandroid.widget.TextView;
  10. publicclassHandlerDemoActivityextendsActivity{
  11. privateButtonb1;
  12. privateButtonb2;
  13. privateButtonb3;
  14. privateButtonb4;
  15. privateProgressBarpb;
  16. privateTextViewtv;
  17. privateHandlerh1_post;
  18. privateHandlerh2_sendmessage;
  19. /**Calledwhentheactivityisfirstcreated.*/
  20. @Override
  21. publicvoidonCreate(BundlesavedInstanceState){
  22. super.onCreate(savedInstanceState);
  23. setContentView(R.layout.main);
  24. b1=(Button)this.findViewById(R.id.button1);
  25. b2=(Button)this.findViewById(R.id.button2);
  26. b3=(Button)this.findViewById(R.id.button3);
  27. b4=(Button)this.findViewById(R.id.button4);
  28. pb=(ProgressBar)this.findViewById(R.id.progressBar1);
  29. tv=(TextView)this.findViewById(R.id.textView1);
  30. b1.setOnClickListener(buttonListener);
  31. b2.setOnClickListener(buttonListener);
  32. b3.setOnClickListener(buttonListener);
  33. b4.setOnClickListener(buttonListener);
  34. h1_post=newHandler();
  35. h2_sendmessage=newHandler(){
  36. @Override
  37. publicvoidhandleMessage(Messagemsg){
  38. pb.setProgress(msg.arg1);
  39. }
  40. };
  41. System.out.println("ThreadId:"+Thread.currentThread().getId());
  42. System.out.println("Threadname:"+Thread.currentThread().getName());
  43. }
  44. RunnableupdateProgressBar=newRunnable(){
  45. inti=0;
  46. @Override
  47. publicvoidrun(){
  48. System.out.println("ThreadId:"+Thread.currentThread().getId());
  49. System.out.println("Threadname:"+Thread.currentThread().getName());
  50. i+=10;
  51. pb.setProgress(i);
  52. try{
  53. Thread.sleep(3000);
  54. }catch(InterruptedExceptione){
  55. //TODOAuto-generatedcatchblock
  56. e.printStackTrace();
  57. }
  58. h1_post.post(updateProgressBar);
  59. if(i==100){
  60. h1_post.removeCallbacks(updateProgressBar);
  61. }
  62. }
  63. };
  64. RunnableupdateProgressBarThread=newRunnable(){
  65. inti=0;
  66. @Override
  67. publicvoidrun(){
  68. System.out.println("ThreadId:"+Thread.currentThread().getId());
  69. System.out.println("Threadname:"+Thread.currentThread().getName());
  70. while((i+=10)<=100){
  71. Messagemsg=h2_sendmessage.obtainMessage();
  72. msg.arg1=i;
  73. h2_sendmessage.sendMessage(msg);
  74. try{
  75. Thread.sleep(3000);
  76. }catch(Exceptione){
  77. e.printStackTrace();
  78. }
  79. }
  80. }
  81. };
  82. privateView.OnClickListenerbuttonListener=newView.OnClickListener(){
  83. @Override
  84. publicvoidonClick(Viewv){
  85. //TODOAuto-generatedmethodstub
  86. switch(v.getId()){
  87. caseR.id.button1:
  88. h1_post.post(updateProgressBar);
  89. tv.setText("whichtest?:Test1");
  90. break;
  91. caseR.id.button2:
  92. newThread(updateProgressBarThread).start();
  93. tv.setText("whichtest?:Test2");
  94. break;
  95. caseR.id.button3:
  96. tv.setText("whichtest?:Test3");
  97. break;
  98. caseR.id.button4:
  99. tv.setText("whichtest?:Test4");
  100. break;
  101. }
  102. }
  103. };
  104. }


结果及说明:程序都是更新进度条操作。我在UI线程,即主线程中打印出了UI线程的ID和名字。

Button1,单纯的异步,我在它会调用的Run方法中也打印出了线程ID和名字。

结果:


显然,通过用Handler h1_post执行的run与主线程是同一个线程下面。

并且在点击Button1以后,我们再点击除了Button2的Button3和Button4会发现,用来显示which test?的字符串更新缓慢。按钮按下效果也会卡住,这些都是说明所有操作都在UI主线程的情况。


再看按下Button2的效果,是多线程异步的:


显然是两个线程了,而且点击其他的按钮反应也不会有卡住得感觉。


所以,在使用Handler的多线程异步时候一定要配合new Thread使用!或者也可以用Android提供的HandlerThread!

更多相关文章

  1. SpringBoot 2.0 中 HikariCP 数据库连接池原理解析
  2. Android(安卓)Service的使用
  3. Android(安卓)四大组件(Activity、Service、BroadCastReceiver、
  4. Android(安卓)Fragment 体系 源码追踪笔记(4)
  5. 【ALearning】第五章 Android相关组件介绍(一)Activity
  6. Android消息处理
  7. Android(安卓)音效流程分析
  8. [置顶] android6.0源码分析之Activity启动过程
  9. Android(安卓)6.0 存储权限管理

随机推荐

  1. 一个切换的Widget
  2. 【059】分享我的 Android 应用
  3. Android最全UI库合集
  4. android 开发谷歌地图的步骤
  5. Android自定义View模拟并实现3D柱状图
  6. 基于32bit系统编译Android(安卓)2.3
  7. Android一些关于分辨率和布局的设置
  8. FileObserver的使用
  9. LGame(Android及J2SE游戏引擎)入门示例—
  10. Android Intent 用法全面总结