您的位置:首页 > 移动开发 > Android开发

android消息线程和消息队列

2014-08-30 11:09 330 查看






基于消息队列的线程通信:
消息队列与线程循环

MessageQueue:
利用链表来管理消息。

Message:

通常由Handler的子类的handleMessage()函数来处理该消息。

由android.os.Handler类来处理消息Message:

Handler:
由Handler来处理消息,由其函数dispatchMessage()完成。
public void dispatchMessage(Message msg) {
if (msg.callback != null) {

handleCallback(msg);

} else {

if (mCallback != null) {

if (mCallback.handleMessage(msg)) {

return;

}

}

handleMessage(msg); //若消息没有指定处理消息的对象,则由Handler的子类来完成。其子类必须实现handleMessage()方法。

}

}

Looper:

Looper与线程关联,一个线程最多有一个Looper。Looper实例保存到宿主线程的线程局部存储中。

指定了Looper就意味着指定了在哪个线程中处理;为消息指定的Handler则决定如何处理消息。

Looper中拥有一个消息队列MessageQueue,该消息队列由Looper创建,属于它所有。

private Looper(boolean quitAllowed) {

mQueue = new MessageQueue(quitAllowed);//创建Looper要处理的消息队列,是否运行线程退出,由消息队列决定。

mRun = true;

mThread = Thread.currentThread();//得到当前线程

}

public static void loop() {

final Looper me = myLooper();

if (me == null) {

throw new RuntimeException("No Looper; Looper.prepare() wasn't called on this thread.");

}

final MessageQueue queue = me.mQueue;

// Make sure the identity of this thread is that of the local process,

// and keep track of what that identity token actually is.

Binder.clearCallingIdentity();

final long ident = Binder.clearCallingIdentity();

for (;;) {

Message msg = queue.next(); // might block//取得一个消息

if (msg == null) {//消息体为空则表示退出

// No message indicates that the message queue is quitting.

return;

}

// This must be in a local variable, in case a UI event sets the logger

Printer logging = me.mLogging;

if (logging != null) {

logging.println(">>>>> Dispatching to " + msg.target + " " +

msg.callback + ": " + msg.what);

}

msg.target.dispatchMessage(msg);//调用消息指定的接收者Handler来处理它

if (logging != null) {

logging.println("<<<<< Finished to " + msg.target + " " + msg.callback);

}

final long newIdent = Binder.clearCallingIdentity();

if (ident != newIdent) {

Log.wtf(TAG, "Thread identity changed from 0x"

+ Long.toHexString(ident) + " to 0x"

+ Long.toHexString(newIdent) + " while dispatching to "

+ msg.target.getClass().getName() + " "

+ msg.callback + " what=" + msg.what);

}

msg.recycle();//丢弃消息,循环再利用

}

}

Handler:消息的处理者。一旦为消息指定了某个特定的处理者Handler,也就确定了在哪个线程的上下文中去处理以及如何处理消息。

实际上是根据Handler的变量mLooper所代表的Looper所在的线程,来决定该Handler运行在哪个线程中。

在一个线程中创建的Handler并不一定运行在该线程中,需要判断该Handler的Looper变量在哪个线程中。

public Handler() {
if (FIND_POTENTIAL_LEAKS) {

final Class<? extends Handler> klass = getClass();

if ((klass.isAnonymousClass() || klass.isMemberClass() || klass.isLocalClass()) &&

(klass.getModifiers() & Modifier.STATIC) == 0) {

Log.w(TAG, "The following Handler class should be static or leaks might occur: " +klass.getCanonicalName());

}

}

mLooper = Looper.myLooper();//通过线程局部存储,获得本线程的Looper:当程序没有另启一个线程时,该Looper就是主线程的Looper。

if (mLooper == null) {

throw new RuntimeException(

"Can't create handler inside thread that has not called Looper.prepare()");

}

mQueue = mLooper.mQueue;

mCallback = null;

}

public void dispatchMessage(Message msg) {
if (msg.callback != null) {

handleCallback(msg);//消息所指定的CallBack,实际就是Runnable

} else {

if (mCallback != null) {

if (mCallback.handleMessage(msg)) {

return;

}

}

handleMessage(msg);//Handler的方法

}

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: