我脑子里有问题,我不知道如何测试。
假设我有一个函数getData
,该函数从一个领域对象中加载数据,这需要5秒钟。
没有协程,我需要在后台线程中调用此方法,以避免阻塞UI。
如果我将getData
更改为暂停功能,并在主线程上调用它,它还会冻结UI线程5秒钟吗?还是就像在getData
函数中调用delay(5000)一样,不会阻塞UI线程?
我想创建一个简单的项目来验证这一点,但是我没有足够大的数据来产生5秒的延迟。
我脑子里有问题,我不知道如何测试。
假设我有一个函数getData
,该函数从一个领域对象中加载数据,这需要5秒钟。
没有协程,我需要在后台线程中调用此方法,以避免阻塞UI。
如果我将getData
更改为暂停功能,并在主线程上调用它,它还会冻结UI线程5秒钟吗?还是就像在getData
函数中调用delay(5000)一样,不会阻塞UI线程?
我想创建一个简单的项目来验证这一点,但是我没有足够大的数据来产生5秒的延迟。
如果我将
getData
更改为suspend
函数,并在主线程上调用它,它还会冻结UI线程5秒钟吗?
是的,协程不能撤消给定代码段进行阻塞函数调用的事实。这是典型的惯用语,您可以用来将对后台线程的阻塞调用移开,然后继续在UI线程上使用它:
myScope.launch {
val result = withContext(Dispatchers.IO) {
// blocking call here
}
// use the result to update the GUI here
}
,
我认为这取决于您的意思
如果我将
getData
更改为暂停功能
suspend
,它将什么都不会改变,即线程将被阻塞,直到得到响应为止。您可以使用Coroutines库中的suspendCoroutine
函数来实现此目的。
抽象示例如下:
suspend fun getData(): String = suspendCoroutine { continuation ->
// 1. Trigger event
serverApi.getData().onResult(
// 3. Resume either with data or error,after callback received from serverApi
onSuccess = {
continuation.resume("Data")
},onError = {
continuation.resume("Error")
}
)
// 2. Suspend after block is finished
}
P.S。上面的情况(从db中获取数据)可能无法工作,因为没有任何要挂起的功能(与网络请求不同,功能一直很忙)。