Kotlin并行协程

保存来自单独的协同程序的多个作业实例是可以接受的。 比方说,我想同时运行两个协程,它们是不相关的,不能在一个协程中发生,但我希望它们并行运行。 在Android中,我应该保存作业实例,这样我就可以在onDestroy方法中取消作业了。 将每项工作分别保存在清单中还是打破某种规定是可以接受的。 我知道在RX他们有订阅为什么Kotlin协同程序中没有相应的东西?

val jobList = arrayListOf<Job>() fun startJob1() { jobList.add(launch { //do some work }) fun startJob1() { jobList.add(launch { //do some other unrelated work }) override fun onDestroy() { super.onDestroy() cancelAllActiveJobs(jobList) } 

这种类型的架构对于协程是否有意义?

这是完全可行的,也没有什么特别的。 看看这个简单的例子,一次创建10万个工作:

 val jobs = List(100_000) { // launch a lot of coroutines and list their jobs launch { delay(1000L) print(".") } } jobs.forEach { it.join() } 

为了使作业可取消,它必须自己检查是否已经从外部取消了,你可以通过循环遍历活动状态: while (isActive)

以下是两个之后取消的作业的示例:

 fun main(args: Array<String>) = runBlocking { val startTime = System.currentTimeMillis() val jobs = arrayListOf<Job>() jobs += launch { var nextPrintTime = startTime var i = 0 while (isActive) { // check if still active if (System.currentTimeMillis() >= nextPrintTime) { println("Job1: Sleeping ${i++} ...") nextPrintTime += 500L } } } //another job jobs += launch { while (isActive) { // check if still active if (System.currentTimeMillis() >= 42) { println("Job2: Sleeping 42 ...") delay(500L) } } } delay(1300L) // delay a bit println("main: Cancelling the sleeping job!") jobs.forEach { it.cancelAndJoin() } // cancels the job and waits for its completion } 

您可以保留一份您启动的Job对象列表,但是您也可以使用现成的亲子作业架构来管理和保留启动的作业列表。

所以,首先,不是一份工作列表,而是定义一个对父作业的引用:

 val job = Job() 

然后,每当你开始一个新的协同程序,你就成为这个工作的孩子

 fun startJob1() { launch(job) { // make it a child //do some work } } fun startJob1() { launch(job) { // make it a child //do some other unrelated work } } 

最后,当你需要销毁你的对象,并取消所有的工作,你只需取消父作业。

 override fun onDestroy() { super.onDestroy() job.cancel() } 

这个应用程序的优点是作业列表是自动管理的。 新协程可以启动并添加到父作业中,并在完成后自动从父作业中移除。

您可以在指南的相应部分阅读更多内容: https : //github.com/Kotlin/kotlinx.coroutines/blob/master/coroutines-guide.md#cancellation-via-explicit-job