协程是什么
- 是一种在程序中处理并发任务的方案,也是这种方案的一个组件
- 协程和线程是属于一个层级的概念
kotlin在jvm中的协程是什么
- 是对线程的包装,线程框架
- 底层用的就是java线程
- 异步操作(切线程)
挂起函数suspend关键字
- 标记和提醒作用,提示方法内部要调用挂起函数做切换线程的作用
- 保证耗时任务放在后台执行
- 为了让函数必须在携程里调用,因为协程里有他所需要的上下文信息,为了能切回原来的线程
协程的优势
- 在频繁切换线程的场景,代码不会嵌套好几层,不方便查看
- 协程启动的时候,是哪个线程,就会自动切回它所在的线程
协程依赖
//协程
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-core:1.3.7'
implementation 'org.jetbrains.kotlinx:kotlinx-coroutines-android:1.3.7'
用协程实现下载网络图片并展示
- 开启一个携程
bt_download.setOnClickListener {
GlobalScope.launch(Dispatchers.Main){
val bitmap = ioCode1()
uiCode1(bitmap)
}
}
- ioCode1方法逻辑代码
private suspend fun ioCode1():Bitmap? {
val bitmap:Bitmap?= withContext(Dispatchers.IO){
Log.d("zyl--","ioCode1 ${Thread.currentThread().name}")
download()
}
return bitmap
}
download()具体下载逻辑实现
private fun download():Bitmap? {
//1.请求url地址获取服务端资源的大小
val url = URL(path)
val openConnection: HttpURLConnection = url.openConnection() as HttpURLConnection
openConnection.requestMethod = "GET"
openConnection.connectTimeout = 10 * 1000
openConnection.connect()
val code = openConnection.responseCode
if(code == 200) {
//获取资源的大小
val filelength = openConnection.contentLength
Log.d("zyl--","size = $filelength")
// //2.在本地创建一个与服务端资源同样大小的一个文件(占位)
val file = File(getFileName(path))
Log.d("zyl--","path = ${file.absolutePath}")
val inputStream = openConnection.inputStream
val fileOutputStream = FileOutputStream(file)
val buffer = ByteArray(1024)
var i = 0
while (inputStream.read(buffer).also { i = it }!=-1){
fileOutputStream.write(buffer, 0, i)
}
// val bitmap = BitmapFactory.decodeStream(inputStream)
return BitmapFactory.decodeFile(file.absolutePath)
}
return null
}
- uiCode1展示
private fun uiCode1(bitmap: Bitmap?) {
Log.d("zyl--","uiCode1 ${Thread.currentThread().name}")
bitmap?.let {
ivImage.setImageBitmap(bitmap)
}
}