Как я могу вернуть ожидаемое значение в Kotlin? - PullRequest
0 голосов
/ 21 ноября 2018

Мне нужно test(), чтобы вернуть игрока из моей базы.Я знаю, что могу использовать обратный вызов, но как я могу заставить эту работу работать с async await?

fun test(): Player {
    launch(UI) {
        val player = async(CommonPool) { MainActivity.database?.playerDao()!!.loadPlayer() }.await()
        return player
    }
}

В настоящее время ошибка составляет return is not allowed here

Например, JavaScriptЯ бы сделал test async тогда await это результат от того, где он называется.

1 Ответ

0 голосов
/ 21 ноября 2018

Невозможно запустить сопрограмму в сыром потоке.По крайней мере, вы должны превратить существующий поток в тот, который вращает цикл событий верхнего уровня.Это достигается с помощью вызова runBlocking в самом верху стека вызовов потока (т. Е. Внутри его метода run()).

В потоке графического интерфейса или любом другом виде потока, который выполняет цикл обработки событий.вам нужен соответствующий Dispatcher, который передает сопрограммы в этот цикл событий.Kotlin уже предоставляет диспетчеры для Swing, JavaFX, Android и т. Д. В этих случаях вам необходимо launch сопрограмма из какого-либо существующего обработчика событий GUI, например:

myScope.launch {
    val player = test()
    ... use the player ...
}

myScope должен быть объектом, которыйCoroutineScope реализует что-то вроде этого:

override val coroutineContext = Dispatchers.Main + SupervisorJob()

Это даст вам возможность полностью отменить все сопрограммы, работающие в той же области, вызывая

coroutineContext[Job]!!.cancel()

Мой пример используетдиспетчер Main, который преобразуется в поток GUI при импорте библиотеки сопрограмм Kotlin, соответствующей вашей структуре пользовательского интерфейса.

Функция test() должна стать suspend fun, которая временно переключает диспетчер в пул потоковдля блокировки операций.Вот как может выглядеть базовый пример:

suspend fun test() = withContext(Dispatchers.IO) {
    MainActivity.database?.playerDao()!!.loadPlayer()
}

Наконец, обратите внимание, я не упоминаю async вообще в этом ответе.async Kotlin имеет очень конкретное назначение, это не общее средство, как на других языках.Его цель - строго параллельная декомпозиция, где вы разбиваете одну задачу на несколько параллельных подзадач.

...