在Kotlin的另一个线程中运行Room Insert的推荐方法

Ali*_*lin 2 android kotlin android-room

我正在Repository执行我想在@Insert新线程中实现的步骤,而不是在UI线程上实现的步骤。

我看到有几种方法可以解决此问题:

  1. 一些样本使用AsyncTask与内doInBackgroundDao电话

  2. 该谷歌向日葵样的用途runOnIoThread是,做的方法IO_EXECUTOR.execute(job),其中IO_EXECUTOR = Executors.newSingleThreadExecutor

  3. 有些似乎用 anko

doAsync{ dao.insert(item) }

推荐的方法是什么?

Epi*_*rce 5

通常,您应该在界面下包装自己的执行器。

public interface Scheduler {
    void runOnThread(Runnable runnable);
}

/**
 * A Scheduler implementation based on ModernAsyncTask with an unbounded task queue.
 **/
public class IoScheduler implements Scheduler {
    private static final int CORE_POOL_SIZE = 5;
    private static final int MAXIMUM_POOL_SIZE = 128;
    private static final int KEEP_ALIVE = 1;

    private static final ThreadFactory sThreadFactory = new ThreadFactory() {
        private final AtomicInteger mCount = new AtomicInteger(1);

        @Override
        public Thread newThread(Runnable r) {
            return new Thread(r, "IoScheduler #" + mCount.getAndIncrement());
        }
    };

    private static final BlockingQueue<Runnable> sPoolWorkQueue =
            new LinkedBlockingQueue<Runnable>();

    /**
     * An {@link Executor} that can be used to execute tasks in parallel.
     */
    private static final Executor THREAD_POOL_EXECUTOR =
         new ThreadPoolExecutor(CORE_POOL_SIZE, MAXIMUM_POOL_SIZE, KEEP_ALIVE,
                 TimeUnit.SECONDS, sPoolWorkQueue, sThreadFactory);

    @Override
    public void runOnThread(Runnable runnable) {
        THREAD_POOL_EXECUTOR.execute(runnable);
    }
}
Run Code Online (Sandbox Code Playgroud)

您通常使用Dagger来提供这些:

@Singleton
public class IoScheduler implements Scheduler {
    @Inject
    IoScheduler() {}
    ...
}

@Module
public class SchedulerModule {
    public static final String BACKGROUND = "BACKGROUND";

    @Named(BACKGROUND) // you can also use @Qualifier
    @Provides
    Scheduler ioScheduler(IoScheduler ioScheduler) {
        return ioScheduler;
    }
}
Run Code Online (Sandbox Code Playgroud)

然后在其他地方使用

@Singleton
public class MyService {
    private final Scheduler ioScheduler;

    @Inject
    MyService(@Named(SchedulerModule.BACKGROUND) Scheduler ioScheduler) { // you can use @Qualifier here instead of @Named
        this.ioScheduler = ioScheduler;
    }
    ....
}
Run Code Online (Sandbox Code Playgroud)

(尽管这ioScheduler对于读取来说更好:对于写入,您可能需要考虑使用单独的单线程执行程序。)


因此,如果您读到最后,实际上就是这种方法:

2.)谷歌向日葵样品用途runOnIoThread它是确实的方法IO_EXECUTOR.execute(job),其中IO_EXECUTOR = Executors.newSingleThreadExecutor

  • 天哪,不,您将为每个插入创建一个新的单线程执行器。创建执行器的单例实例并在全局范围内使用它进行写入。 (2认同)