我想在Kotlin协程被取消后做一个小单词。(我在这个协程中有一个延迟函数)。通过使用线程,我可以捕获InterruptedException并做一些工作,然后完成线程。但是使用Kotlin协程,当执行到达延迟函数时,它会在调用cancel后立即取消作业。我知道如果我在协程中使用Thread.sleep,它会完成这项工作。但有没有更好的解决办法呢我想在取消作业后继续作业,如果作业被取消,则不运行某些代码
InterruptedException
Thread.sleep
0s0u357o1#
使用withContext(NonCancellable) { ... }。在此上下文中运行的代码不会对外部协程的取消做出React。这意味着像delay这样的函数不会抛出CancellationException。您可以将其与try/finally结合使用,以在取消协程后运行挂起代码。在这个例子中,对delay的调用将延迟协程的终止,并且不会抛出CancellationException,即使协程已经被取消。
withContext(NonCancellable) { ... }
delay
CancellationException
try
finally
try { // do stuff } finally { withContext(NonCancellable) { delay(1000) } }
这个机制在Kotlin文档中有更详细的描述。如果你想知道更多细节,我还写了一个longer article,说明它是如何工作的。请注意,您不能“取消”协程。将try/finally与NonCancellable结合使用主要用于运行清理任务。协程Job仍然被标记为已取消,协程仍然应该确保它最终终止。
NonCancellable
Job
1条答案
按热度按时间0s0u357o1#
使用
withContext(NonCancellable) { ... }
。在此上下文中运行的代码不会对外部协程的取消做出React。这意味着像delay
这样的函数不会抛出CancellationException
。您可以将其与
try
/finally
结合使用,以在取消协程后运行挂起代码。在这个例子中,对
delay
的调用将延迟协程的终止,并且不会抛出CancellationException
,即使协程已经被取消。这个机制在Kotlin文档中有更详细的描述。如果你想知道更多细节,我还写了一个longer article,说明它是如何工作的。
请注意,您不能“取消”协程。将
try
/finally
与NonCancellable
结合使用主要用于运行清理任务。协程Job
仍然被标记为已取消,协程仍然应该确保它最终终止。