Я пытаюсь запустить несколько задач параллельно, но задачи независимы, поэтому, если один из дочерних сопрограмм завершится с ошибкой, я не хочу, чтобы его братья и сестры тоже потерпели неудачу. В приведенном ниже коде я использовал coroutineScope для создания новой области действия, в которой выполняются эти задачи, и запускал 5 асинхронных задач, каждая из которых отправляла свой идентификатор и время задержки, которое он должен ждать. Вторая сопрограмма бросает исключение. В этом случае код выполняет то, что я хочу, он вычисляет сумму успешно завершенных и неудавшихся заданий, возвращающих 0.
Однако я читаю, что в kotlinx также есть supervisorScope. библиотека, которая должна быть предпочтительнее, чем coroutineScope (которая отменяет родительский / родной брат, если исключение не обрабатывается), поскольку задачи не зависят от других. Я не уверен, почему мне следует перейти на использование supervisorScope, поскольку я получаю нужный результат с помощью coroutineScope.
Q1 : Если я перехожу на supervisorScope, в моем асинхронном случае что-то изменитсяblocks?
Q2 : Принято ли перехватывать какие-либо исключения внутри асинхронного блока и не позволять что-либо распространяться на его родительский элемент? Я знаю, что вы также можете перехватывать исключения во время фазы .await (), но так ли это должно быть?
runBlocking {
coroutineScope {
val job1 = async<Int> {
try {
request(1, 1000)
} catch (e: Exception) {
println("Job 1 failed with $e")
0
}
}
val job2 = async<Int> {
try {
request(2, 2000)
throw Exception("cancelling Job 2")
} catch (e: Exception) {
println("Job 2 failed: $e")
0
}
}
val job3 = async {
try {
request(3, 3000)
} catch (e: Exception) {
println("Job 3 failed with $e")
0
}
}
val job4 = async {
try {
request(4, 4000)
} catch (e: Exception) {
println("Job 4 failed with $e")
0
}
}
val job5 = async {
try {
request(5, 5000)
} catch (e: Exception) {
println("Job 5 failed with $e")
0
}
}
val result = job1.await() + job2.await() + job3.await() + job4.await() + job5.await()
println(result.toString())
}
println("Finished")
}
suspend fun request(id: Int, time: Long): Int {
println("Job $id started")
delay(time)
println("Job $id finished")
return id
}