【发布时间】:2021-07-25 17:18:47
【问题描述】:
我正在研究如何使用 Android 中的 Room 将数据写入 SQlite 数据库的教科书示例。显然,我们不能从主线程将数据写入数据库,但我们需要一个后台线程。在我的书中,我们所做的是,我们创建了一个额外的类AppExecutors,其内容如下:
public class AppExecutors {
private final Executor _diskIO;
private final Executor _networkIO;
private final Executor _mainThread;
private AppExecutors(Executor diskIO, Executor networkIO, Executor mainThread) {
_diskIO = diskIO;
_networkIO = networkIO;
_mainThread = mainThread;
}
public AppExecutors() {
this(Executors.newSingleThreadExecutor(),
Executors.newFixedThreadPool(3),
new MainThreadExecutor());
}
public Executor diskIO() {
return _diskIO;
}
public Executor networkIO() {
return _networkIO;
}
public Executor mainThread() {
return _mainThread;
}
private static class MainThreadExecutor implements Executor {
private Handler mainThreadHandler = new Handler(Looper.getMainLooper());
@Override
public void execute(Runnable command) {
mainThreadHandler.post(command);
}
}
}
然后,在 MainActivity 内部,它也包含 UI,即按钮,当点击时触发一个动作,我们调用
getApp().getExecutors().diskIO().execute(() -> {
...
}
其中getApp().getExecutors() 返回AppExecutors 的新实例。
这是我的问题:
我知道getApp().getExecutors().mainThread().execute(() -> {...} 被传递了一个新的Runnable,并且这个Runnable 被提供给主线程的消息队列。 looper 将每个线程从消息队列中取出并执行。
但是,getApp().getExecutors().diskIO().execute(() -> {...} 的情况有所不同。
传递给它的 Runnable 显然是在后台线程中执行的。 Executors.newSingleThreadExecutor() 似乎正在开辟一个新线程。但是没有与该线程关联的处理程序或消息队列。所以,我想知道,这个线程在执行后不会关闭吗?一旦线程关闭,我们就不能再次打开同一个线程。这对我来说有点困惑,线程不应该保持打开状态吗?
我现在已经阅读了 ExecutorService ,显然这个服务只是让线程保持打开状态。但是话又说回来,这不是 messageque 和处理程序正在做的事情吗?那么这有什么不同呢?
【问题讨论】:
标签: android multithreading executorservice