我是安卓系统的新手。我想知道Looper类做什么,以及如何使用它。我已经阅读了Android Looper类文档,但我无法完全理解它。 我在很多地方见过它,但无法理解它的目的。谁能帮我定义一下Looper的目的,如果可能的话,也给我一个简单的例子?
当前回答
java线程的生命周期在run()方法完成后结束。同一线程不能再次启动。
Looper将普通线程转换为消息循环。Looper的主要方法有:
void prepare ()
将当前线程初始化为循环程序。这使您有机会创建处理程序,然后在实际开始循环之前引用此循环程序。请确保在调用此方法后调用loop(),并通过调用quit()结束它。
void loop ()
在此线程中运行消息队列。确保调用quit()来结束循环。
void quit()
退出循环器。 导致loop()方法终止,而不处理消息队列中的任何其他消息。
Janishar的这篇mindorks文章很好地解释了核心概念。
循环程序与线程相关联。如果你在UI线程上需要Looper, loop . getmainlooper()将返回相关的线程。
您需要将Looper与Handler相关联。
Looper, Handler和HandlerThread是Android解决异步编程问题的方法。
有了Handler之后,就可以调用下面的api了。
post (Runnable r)
导致Runnable r被添加到消息队列。可运行对象将在附加此处理程序的线程上运行。
boolean sendMessage (Message msg)
在当前时间之前的所有挂起消息之后,将消息压入消息队列的末尾。它将在附加到此处理程序的线程中的handleMessage(Message)中接收。
HandlerThread是一个方便的类,用于启动具有循环程序的新线程。循环程序可以用来创建处理程序类
在某些情况下,你不能在UI线程上运行可运行任务。 例如,网络操作:在套接字上发送消息,打开URL并通过读取InputStream获取内容
在这些情况下,HandlerThread很有用。你可以从HandlerThread获取Looper对象,并在HandlerThread上创建Handler而不是主线程。
HandlerThread代码是这样的:
@Override
public void run() {
mTid = Process.myTid();
Looper.prepare();
synchronized (this) {
mLooper = Looper.myLooper();
notifyAll();
}
Process.setThreadPriority(mPriority);
onLooperPrepared();
Looper.loop();
mTid = -1;
}
参考下面的示例代码:
Android:在线程中吐司
其他回答
循环器有一个同步的messagqueuue,用于处理放置在队列上的消息。
它实现了线程特定的存储模式。
每个线程只有一个Looper。关键方法包括prepare()、loop()和quit()。
prepare()将当前线程初始化为循环程序。prepare()是使用ThreadLocal类的静态方法,如下所示。
public static void prepare(){
...
sThreadLocal.set
(new Looper());
}
在运行事件循环之前,必须显式地调用Prepare()。 loop()运行事件循环,等待消息到达特定线程的消息队列。一旦接收到下一个Message, loop()方法将该Message分派给它的目标处理程序 Quit()关闭事件循环。它不会终止循环,而是将一条特殊消息编入队列
Looper可以通过几个步骤在线程中编程
扩展的线程 调用loop .prepare()将Thread初始化为Looper 创建一个或多个Handler来处理传入消息 调用loop .loop()来处理消息,直到循环被告知quit()。
Android Looper是一个包装器,用于将messagqueuue附加到线程,并管理队列处理。它在Android文档中看起来非常神秘,很多时候我们可能会面临与Looper相关的UI访问问题。如果我们不了解基础知识,就很难处理。
这是一篇文章,解释了Looper的生命周期,如何使用它,以及在Handler中使用Looper
循环器=线程+消息队列
这个答案与问题无关,但looper的使用以及人们在这里的所有答案中创建处理程序和looper的方式都是明显的坏习惯(尽管有些解释是正确的),我不得不发布这个:
HandlerThread thread = new HandlerThread(threadName);
thread.start();
Looper looper = thread.getLooper();
Handler myHandler = new Handler(looper);
以及一个完整的实现
在Service中处理多个下拉或上传项是一个更好的例子。
Handler和AsnycTask通常用于在UI(线程)和工作线程之间传播事件/消息或延迟操作。所以它们与UI更相关。
循环程序在后台处理线程相关队列中的任务(Runnables, Futures) -即使没有用户交互或显示UI(应用程序在调用期间在后台下载文件)。
什么是环形使者?
Looper是一个用于执行队列中的消息(可运行对象)的类。普通线程没有这样的队列,例如简单线程没有任何队列。它执行一次,方法执行完成后,线程将不再运行另一个Message(Runnable)。
我们可以在哪里使用Looper类?
如果有人想要执行多个消息(Runnables),那么他应该使用负责在线程中创建队列的Looper类。 例如,在编写从internet下载文件的应用程序时,我们可以使用Looper类将要下载的文件放入队列中。
它是如何工作的?
有prepare()方法来准备Looper。然后,您可以使用loop()方法在当前线程中创建一个消息循环,现在您的Looper已经准备好在队列中执行请求,直到退出循环。
下面是您可以准备Looper的代码。
class LooperThread extends Thread {
public Handler mHandler;
@Override
public void run() {
Looper.prepare();
mHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
// process incoming messages here
}
};
Looper.loop();
}
}
推荐文章
- 警告:API ' variable . getjavacompile()'已过时,已被' variable . getjavacompileprovider()'取代
- 安装APK时出现错误
- 碎片中的onCreateOptionsMenu
- TextView粗体通过XML文件?
- 如何使线性布局的孩子之间的空间?
- 自动化invokerrequired代码模式
- DSL元素android.dataBinding。enabled'已过时,已被'android.buildFeatures.dataBinding'取代
- ConstraintLayout:以编程方式更改约束
- PANIC: AVD系统路径损坏。检查ANDROID_SDK_ROOT值
- 如何生成字符串类型的buildConfigField
- Recyclerview不调用onCreateViewHolder
- Android API 21工具栏填充
- Android L中不支持操作栏导航模式
- c#线程安全快速(est)计数器
- 如何将此foreach代码转换为Parallel.ForEach?