Getting started with Android kotlin collaboration

Android officials recommend using concurrency to deal with asynchronous problems. The following are the characteristics of the collaborative process:

Firstly, kotlin and coprocess need to be introduced into the project. Then use the process to initiate the network request.

Kotlin is introduced into the Android project. Refer to the Android project to use kotlin

With KT, the co process is introduced

dependencies {
    implementation "org.jetbrains.kotlinx:kotlinx-coroutines-android:1.3.9" // 协程
}

Unlike the kotlin project, which directly uses globalscope, this example uses coprocessors in the ViewModel. Viewmodelscope is required.

The following corvm1 inherits the ViewModel.

import androidx.lifecycle.viewmodel
import androidx.lifecycle.viewmodelScope // 引入
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch

class CorVm1 : viewmodel() {

    companion object {
        const val TAG = "rfDevCorVm1"
    }

    fun cor1() {
        viewmodelScope.launch { Log.d(TAG,"不指定dispatcher ${Thread.currentThread()}") }
    }
}

Calling the COR1 () method in the button click listener, you can see that the association is in the main thread.

不指定dispatcher Thread[main,5,main]

Since this collaboration is started through viewmodelscope, it is executed within the scope of ViewModel. If the ViewModel is destroyed because the user leaves the screen, the viewmodelscope will be automatically cancelled and all running collaborations will be cancelled.

The launch () method can specify the thread to run. You can pass in dispatchers to specify the thread to run.

Let's take a brief look at dispatchers in the kotlinx.coroutines package. It has four attributes:

Are started by clicking on events

// CorVm1.kt

fun ioCor() {
    viewmodelScope.launch(Dispatchers.IO) {
        Log.d(TAG,"IO 协程 ${Thread.currentThread()}")
    }
}

fun defaultCor() {
    viewmodelScope.launch(Dispatchers.Default) {
        Log.d(TAG,"Default 协程 ${Thread.currentThread()}")
    }
}

fun mainCor() {
    viewmodelScope.launch(Dispatchers.Main) { Log.d(TAG,"Main 协程 ${Thread.currentThread()}") }
}

fun unconfinedCor() {
    viewmodelScope.launch(Dispatchers.Unconfined) {
        Log.d(TAG,"Unconfined 协程 ${Thread.currentThread()}")
    }
}

Run log

IO 协程 Thread[DefaultDispatcher-worker-1,main]
Main 协程 Thread[main,main]
Default 协程 Thread[DefaultDispatcher-worker-1,main]
Unconfined 协程 Thread[main,main]

As can be seen from the above comparison, if you want to use background threads, you can consider dispatchers.io. Default also uses the defaultdispatcher-worker-1 thread.

Network requests cannot be made in the main thread. We put the requests on the thread reserved for IO operations. Some messages are sent with mutablelivedata.

// CorVm1.kt
val info1LiveData: mutablelivedata<String> = mutablelivedata()

private fun reqGet() {
    info1LiveData.value = "发起请求"
    viewmodelScope.launch(Dispatchers.IO) {
        val url = URL("https://www.baidu.com/s?wd=abc")
        try {
            val conn = url.openConnection() as HttpURLConnection
            conn.requestMethod = "GET"
            conn.connectTimeout = 10 * 1000
            conn.setRequestProperty("Cache-Control","max-age=0")
            conn.doOutput = true
            val code = conn.responseCode
            if (code == 200) {
                val baos = ByteArrayOutputStream()
                val inputStream: InputStream = conn.inputStream
                val inputS = ByteArray(1024)
                var len: Int
                while (inputStream.read(inputS).also { len = it } > -1) {
                    baos.write(inputS,len)
                }
                val content = String(baos.toByteArray())
                baos.close()
                inputStream.close()
                conn.disconnect()
                info1LiveData.postValue(content)
                Log.d(TAG,"net1: $content")
            } else {
                info1LiveData.postValue("网络请求出错 $conn")
                Log.e(TAG,"net1: 网络请求出错 $conn")
            }
        } catch (e: Exception) {
            Log.e(TAG,"reqGet: ",e)
        }
    }
}

Take a look at the flow of this network request

The content of this article comes from the network collection of netizens. It is used as a learning reference. The copyright belongs to the original author.
THE END
分享
二维码
< <上一篇
下一篇>>