進程是資源分配的最小單位,線程是程序執行的最小單位。html
進程有本身的獨立地址空間,每啓動一個進程,系統就會爲它分配地址空間,創建數據表來維護代碼段、堆棧段和數據段,這種操做很是昂貴。而線程是共享進程中的數據的,使用相同的地址空間,所以CPU切換一個線程的花費遠比進程要小不少,同時建立一個線程的開銷也比進程要小不少。android
爲了加大一個應用可以使用的內存經過多進程來獲取多分內存空間 經過給四大組件指定android:process屬性能夠輕易開啓多進程程序員
跨進程通訊方式有:數據庫
1. 經過Intent(Bundle)附加extras來傳遞信息bash
2. 經過共享文件來共享數據多線程
3. 採用Binder方式來是想跨進程通訊app
4. 採用ContentProvider異步
5. 採用socketsocket
延申到android崩潰一樣道理。async
app中大量Web頁面的使用容易致使App內存佔用巨大,存在內存泄露,崩潰率高等問題,WebView獨立進程的使用是解決Android WebView相關問題的一個合理的方案。
kotlin協程是一種用戶態的輕量級線程。一個進程能夠擁有多個線程同樣,一個線程也能夠擁有多個協程。
協程不是被操做系統內核所管理,而徹底是由程序所控制(也就是在用戶態執行)。
協程的開銷遠遠小於線程的開銷。
協程的特色在因而單線程執行,那和多線程比,協程有何優點?換句話說,協程的出現解決了線程的那些痛點。
進程:擁有本身獨立的堆和棧,既不共享堆,也不共享棧,進程由操做系統調度; 線程:擁有本身獨立的棧和共享的堆,共享堆,不共享棧,標準線程由操做系統調度; 協程:擁有本身獨立的棧和共享的堆,共享堆,不共享棧,協程由程序員在協程的代碼裏顯示調度。
協程主要是讓原來要使用"異步+回調方式"寫出來複雜代碼,簡化成能夠用看似同步的方式,這樣咱們就能夠按串行的思惟模式去組織本來分散在不一樣上下文的代碼邏輯。也加強了程序的可讀性。
//----例如:僞代碼----
launch(Background) {
//執行耗時操做
val bitmap = MediaStore.getBitmap(uri)
launch(UI) {
//更新UI
imageView.setImageBitmap(bitmap)
}
}
複製代碼
ext.kotlin_version = '1.3.11'
dependencies {
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
}
複製代碼
implementation "org.jetbrains.kotlinx:kotlinx-coroutines-core:1.1.0"
//或使用android
implementation "org.jetbrains.kotlinx:kotlinx-coroutines-android:1.1.0"
複製代碼
//在module的build.gradle中聲明
kotlin {
experimental {
coroutines 'enable'
}
}
複製代碼
//launch
launch{
delay(1000)
println("launch")
}
//async 有返回值
async {
delay(1000)
println("async")
//async 纔能有return
return@async ""
}
複製代碼
Dispatchers.Default 共享後臺線程池裏的線程
Dispatchers.Main Android主線程
Dispatchers.IO 共享後臺線程池裏的線程
Dispatchers.Unconfined 不限制,使用父Coroutine的現場
newSingleThreadContext 使用新的線程
/**
* 上下文
*/
launch { // 運行在父協程的上下文中,即 runBlocking 主協程
println("main runBlocking : I'm working in thread ${Thread.currentThread().name}")
}
launch(Dispatchers.Default) { // 將會獲取默認調度器
println("Default : I'm working in thread ${Thread.currentThread().name}")
}
launch(Dispatchers.Main) { // Android主線程
println("Main : I'm working in thread ${Thread.currentThread().name}")
}
launch(Dispatchers.IO) { // 共享後臺線程池裏的線程
println("IO : I'm working in thread ${Thread.currentThread().name}")
}
launch(Dispatchers.Unconfined) { // 不受限的——將工做在主線程中
println("Unconfined : I'm working in thread ${Thread.currentThread().name}")
}
launch(newSingleThreadContext("MyOwnThread")) { // 將使它得到一個新的線程
println("newSingleThreadContext: I'm working in thread ${Thread.currentThread().name}")
}
複製代碼
thread 線程之間採起的是競爭 cpu 時間段的方法,誰搶到誰運行,由系統內核控制,對咱們來講是不可見不可控的。協程不一樣,協程之間不用競爭、誰運行、誰掛起、何時恢復都是由咱們本身控制的。
runBlocking {
val deferred1 = async(Dispatchers.Default) {
println(Thread.currentThread())
"hello1"
}
async(Dispatchers.Default){
println(Thread.currentThread())
println("hello2")
//await()能夠返回當前協程的執行結果: hello1
println(deferred1.await())
}
}
複製代碼
kotlin彙總介紹: kotlin協程指南
工做須要,目前正在寫一個kotlin社交項目。項目中用到room存儲數據,在線程裏經過Dao操做本地數據庫,根據Dao數據返回到主線程更新UI。這個線程切換,使用協程來操做,代碼簡潔易讀。因此花點時間瞭解下!
Kotlin中的協程也是經過線程池來實現的。而在Kotlin中,在線程之上也創建了在線程中相似於Looper+Handler的機制,讓協程能夠在多個線程中切換,以及進行數據的傳遞。