AsyncQueryHandler类的简单分析

AsyncQueryHandler 类是Android为开发者提供的一个辅助类,方便开发者更简单方便的完成ContentResolver的增删改查操作。

使用非常简单,提供了四个用于增删改查的方法:

startQuery  startInsert  startUpdate   startDelete  

每一项执行完成后都有一个相应的回调函数

onQueryComplete  onInsertComplete  onUpdateComplete  onDeleteComplete

所以,你只需要new一个AsyncQueryHandler 对象,并且实现相应的回调方法来完成你的业务逻辑,其他的工作它都帮你做了。

本文主要是分析它是怎么完成这个工作的。


首先看一下该类的定义:public abstract class AsyncQueryHandler extends Handler ,它是Handler的一个子类,怎么它就能完成异步操作了呢?然后我们在看看我们创建这个对象时发生了什么?

public AsyncQueryHandler(ContentResolver cr) {
        super();
        mResolver = new WeakReference<ContentResolver>(cr);   // 1.
        synchronized (AsyncQueryHandler.class) {
            if (sLooper == null) {
                HandlerThread thread = new HandlerThread("AsyncQueryWorker"); // 2.
                thread.start();
                sLooper = thread.getLooper(); // 3.
            }
        }
        mWorkerThreadHandler = createHandler(sLooper); // 4.
    }


这个构造函数做了4项工作:

1. 创建ContentResolver对象的弱引用,防止内存泄露,原强引用是我们在new AsyncQueryHandler时传进来的;

2. 创建一个HandlerThread对象,HandlerThread对象就不做介绍了,它是一个Thread ,然后调用start()方法启动该Thread;

3. 第2步就是为了第3步拿到Looper对象,这也是该类的灵魂点,要拿到子线程的Looper对象,而非主线程的Looper。这就为异步工作做好了准备工作;

4.通过第3步得到的子线程的Looper对象来创建一个Handler,这个Handler就工作在了子线程的消息循环里面,它就可以向子线程的消息队列存放消息,从而完成相应的任务。

其实,仅从AsyncQueryHandler的构造函数就基本把这个辅助类的实现原理看清楚了,接下来再分析的话就是具体Handler怎么执行了。

在贴一下子线程中的Handler的handleMessage()方法,代码有省略,很容易看出来它就是在使用ContentResolver 来执行具体的增删改查。

 

public void handleMessage(Message msg) {
            final ContentResolver resolver = mResolver.get();
            if (resolver == null) return;
...
            switch (event) {
                case EVENT_ARG_QUERY:
                    Cursor cursor;
                    try {
                        cursor = resolver.query(args.uri, args.projection,
                                args.selection, args.selectionArgs,
                                args.orderBy);
 ...
                    break;
                case EVENT_ARG_INSERT:
                    args.result = resolver.insert(args.uri, args.values);
                    break;
                case EVENT_ARG_UPDATE:
                    args.result = resolver.update(args.uri, args.values, args.selection,
                            args.selectionArgs);
                    break;
                case EVENT_ARG_DELETE:
                    args.result = resolver.delete(args.uri, args.selection, args.selectionArgs);
                    break;
            }


还有一点要讲的是AsyncQueryHandler也是Handler,但是是运行在主线程的,这是我们希望的,这样才能在完成子线程任务后与主线程进行通信,从而可以直接方便地执行主线程的逻辑。

这里需要知道Handler, Thread,HandlerThread, Looper,MessageQueue的相关概念,否则这个类的原理分析起来就有一点困难了。




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值