使科特林异步调用同步

auser:

我有一个API我在无法控制....它包含做了一些工作,异步地返回结果的方法。我想在我的应用程序的部分同步调用此方法。我已经通过添加类做到了这一点ResultHandler,其捕获并返回结果。是否有这样做比我已经做了以下的方式更好的办法?也许使用标准科特林(或Java作为最后的手段)库的方法。我更倾向于将用于awaitReply返回结果,并删除CountdownLatch

class Main {
    companion object {
        @JvmStatic

        fun main(args: Array<String>) {
            val result1 = Main().nonAsyncMethod1(arrayListOf(1, 2, 3, 4, 5))
            result1.elements.forEach { println(it) }
        }
    }

    class Result1(var elements: Collection<String>)

    fun asyncMethod1(x: Collection<Int>, callback: (Result1) -> Unit) {
        Thread().run {
            // do some calculation
            Thread.sleep(1000)
            callback(Result1(x.map { "\"$it\"" }.toList()))
        }
    }

    private fun nonAsyncMethod1(entities: Collection<Int>): Result1 {
        val resultHandler = ResultHandler<Result1>()

        awaitReply<Result1> {
            asyncMethod1(entities, resultHandler)
        }
        return resultHandler.getResponse()
    }

    open class ResultHandler<T : Any> : (T) -> Unit {
        private lateinit var response: T
        private val latch = CountDownLatch(1)

        override fun invoke(response: T) {
            latch.countDown()
            this.response = response
        }

        fun getResponse(): T {
            latch.await()
            return response
        }
    }

    private fun <T : Any> awaitReply(call: () -> Unit) {
        return call.invoke()
    }
}
auser:

由于从the_dani提示

我设法来使用以下作为协同程序“详细的解决方案包装回调 ”的科特林第协同程序文件:

class Main {
    companion object {
        @JvmStatic

        fun main(args: Array<String>) = runBlocking {
            val result1 = Main().nonAsyncMethod1(arrayListOf(1, 2, 3, 4, 5))
            result1.elements.forEach { println(it) }
        }
    }

    class Result1(var elements: Collection<String>)

    fun asyncMethod1(x: Collection<Int>, callback: (Result1) -> Unit) {
        Thread().run {
            // do some calculation
            Thread.sleep(1000)
            callback(Result1(x.map { "\"$it\"" }.toList()))
        }
    }

    suspend fun nonAsyncMethod1(entities: Collection<Int>): Result1 = suspendCoroutine {
        cont ->
            asyncMethod1(entities) { cont.resume(it) }
    }
}

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章