浅谈Android之于新线程创建Handler

Handler作为Android中举足轻重的知识点,无论是在实际开发还是在面试中都经常会用到,并且在网上关于Handler的讲解不胜枚举,本人深知水平有限,因此仅在此做一下自己的小结,权当学习中的笔记。

之前写过一篇有关Handler中基本方法使用的一篇文章http://blog.csdn.net/james_shu/article/details/53367035,本篇基于此,写出一些其他的新内容。

Android中的异步消息处理主要由4个部分组成:Message、Handler、MessageQueue和Looper。其中,
Message:Message是在线程之间传递的消息,当我们在不同的线程中传递数据时,Handler将我们要传递的信息封装到Message中然后进行传递。
Handler:Handler主要是用于发送消息,接受并处理消息。
MessageQueue:消息队列,它主要用于存放Handler发送的消息。存放于消息队列中的消息等待被处理,每一个线程中只会有一个MessageQueue对象。
Looper:Looper是每一个线程中的MessageQueue的管家,调用Looper的loop()方法之后就会进入到一个无限循环中,然后当发现MessageQueue中存在一条消息就会将其取出并将这条消息传递到Handler的handleMessage()方法,每一个线程中只会有一个Looper对象。

这里应该提到的一点是:
主线程中默认初始化了Looper,因此我们可以在创建Handler之后直接发送消息和处理消息,其中处理消息一定是创建Handler所在的线程中处理消息,而发送消息就可以在不同的线程中发送消息。
当我们创建一个新的线程的时候(不在主线程时),此时我们如果需要在新线程中创建Handler作为其他线程与所创建的当前线程的通信的桥梁时,我们需要首先创建Looper对象,然后创建Handler对象。

下面我们以计算指定区间的质数为例来介绍在新线程中创建Handler的用法:
布局文件:

  <EditText
        android:id="@+id/etNum"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />
    <Button
        android:onClick="calculate"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="点击得到处理的结果"
        />

代码:

 @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        initView();
        calThread=new CalThread();
        calThread.start();
    }

    private void initView() {
        etNum= (EditText) findViewById(R.id.etNum);//使用Handler将用户在UI界面输入的数值上限动态的传递给新启动的线程

    }


    class CalThread extends Thread{
        public Handler mHandler;                //在新线程中创建Handler,作为主线程与新线程的通信的桥梁
        //在主线程中系统已经初始化了一个Looper对象,因此程序可以直接创建handler对象然后使用创建的Handler对象来发送消息和处理消息
        //然而当自己创建一个新的线程的时候,为了使用自己创建的Handler对象,此时就应该自己同时创建一个Looper对象,此时Handler的功能才算是完整的
        @Override
        public void run() {
            super.run();
            Looper.prepare();
            mHandler=new Handler(){
                //定义处理消息的方法
                @Override
                public void handleMessage(Message msg) {
                    super.handleMessage(msg);
                    if(msg.what==0x123){
                        int upper=msg.getData().getInt(UPPER_NUM);
                        List<Integer> nums=new ArrayList<Integer>();
                        //计算从二开始的质数
                        outer:
                        for (int i=2;i<=upper;i++){
                            for (int j=2;j<=Math.sqrt(i);j++){
                                if(i!=2&&i%j==0){
                                    continue outer;
                                }
                            }
                            nums.add(i);
                        }
                        Toast.makeText(MainActivity.this,nums.toString(),Toast.LENGTH_SHORT).show();
                    }
                }
            };
            Looper.loop();
        }
    }

    public void calculate(View view){
        Message msg=new Message();
        msg.what=0x123;
        Bundle bundle=new Bundle();
        bundle.putInt(UPPER_NUM,Integer.parseInt(etNum.getText().toString()));
        msg.setData(bundle);
        calThread.mHandler.sendMessage(msg);
    }
发布了123 篇原创文章 · 获赞 47 · 访问量 14万+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章