ユーザ用ツール

サイト用ツール


kotlin:coroutines

差分

この文書の現在のバージョンと選択したバージョンの差分を表示します。

この比較画面にリンクする

両方とも前のリビジョン 前のリビジョン
次のリビジョン
前のリビジョン
kotlin:coroutines [2019/10/12 16:19]
ips
kotlin:coroutines [2020/01/14 07:03] (現在)
ips [まとめ]
ライン 2: ライン 2:
  
 [[https://​kotlinlang.org/​docs/​tutorials/​coroutines/​coroutines-basic-jvm.html|Your first coroutine with Kotlin]] [[https://​kotlinlang.org/​docs/​tutorials/​coroutines/​coroutines-basic-jvm.html|Your first coroutine with Kotlin]]
 +
 +[[https://​github.com/​pljp/​kotlinx.coroutines/​blob/​japanese_translation/​docs/​basics.md|pljp/​kotlinx.coroutines]]
  
 ===== coroutineの使い方 ===== ===== coroutineの使い方 =====
ライン 119: ライン 121:
 Sum: 1784293664 Sum: 1784293664
 </​code>​ </​code>​
 +
 +===== mainスレッド(UIスレッド)へのアクセスが簡単 =====
 +
 +launchやasyncで新しいcoroutineを作成するが、Dispatchers.Mainで簡単にmainスレッドを呼び出せる。
 +今までのdoInBackgroundでpublishProgressを使ってonProgressUpdateを呼び出すようなことをしなくてよくなる。
 +
 +<code kotlin>
 +package com.nekotype.ips.myapplication
 +
 +import androidx.appcompat.app.AppCompatActivity
 +import android.os.Bundle
 +import android.util.Log
 +import kotlinx.android.synthetic.main.activity_main.*
 +import kotlinx.coroutines.*
 +import java.text.SimpleDateFormat
 +import java.util.*
 +
 +class MainActivity : AppCompatActivity() {
 +
 +    override fun onCreate(savedInstanceState:​ Bundle?) {
 +        super.onCreate(savedInstanceState)
 +        setContentView(R.layout.activity_main)
 +
 +        val format = SimpleDateFormat("​kk:​mm:​ss"​)
 +
 +        Log.d("​async",​ "​${text1.text} ${format.format(Date())} : ouerLaunch1 : ${Thread.currentThread().name}\n\n"​)
 +
 +        GlobalScope.launch {
 +
 +            Log.d("​async",​ "​${text1.text} ${format.format(Date())} : inLaunch1 : ${Thread.currentThread().name}\n\n"​)
 +
 +            async{
 +                delay(3000)
 +                Log.d("​async",​ "​${text1.text} ${format.format(Date())} : async1 : ${Thread.currentThread().name}\n\n"​)
 +            }
 +
 +            Log.d("​async",​ "​${text1.text} ${format.format(Date())} : inLaunch2 : ${Thread.currentThread().name}\n\n"​)
 +
 +
 +            async(Dispatchers.Main) {
 +                delay(1000)
 +                Log.d("​async",​ "​${text1.text} ${format.format(Date())} : async2 : ${Thread.currentThread().name}\n\n"​)
 +            }
 +
 +            async {
 +                delay(500)
 +                Log.d("​async","​${text1.text} ${format.format(Date())} : async3 : ${Thread.currentThread().name}\n\n"​)
 +                async(Dispatchers.Main) {
 +                    Log.d("​async",​ "​${text1.text} ${format.format(Date())} : inAsync3 : ${Thread.currentThread().name}\n\n"​)
 +                }
 +
 +            }
 +
 +        }
 +
 +        Log.d("​async","​${text1.text} ${format.format(Date())} : ouerLaunch2 : ${Thread.currentThread().name}\n\n"​)
 +    }
 +}
 +
 + ↓
 +
 +05:32:14 : ouerLaunch1 : main
 +05:32:14 : ouerLaunch2 : main
 +05:32:14 : inLaunch1 : DefaultDispatcher-worker-1
 +05:32:14 : inLaunch2 : DefaultDispatcher-worker-1
 +05:32:14 : async3 : DefaultDispatcher-worker-1
 +05:32:14 : inAsync3 : main // ⇒ worker-1 の内側からmainを呼び出している
 +05:32:15 : async2 : main
 +05:32:17 : async1 : DefaultDispatcher-worker-3
 +
 +</​code>​
 +
 +<code kotlin>
 +        Log.d( ​ "​coroutine","​start"​)
 +        GlobalScope.launch(Dispatchers.Main) {
 +                Log.d( ​ "​coroutine","​coroutin"​)
 +                Text.text="​click"​ // 画面のテキストを変更する
 +        }
 +        Log.d( ​ "​coroutine","​end"​)
 +   ↓
 +2020-01-14 06:​24:​17.847 7602-7602/​com.nekotype.ips.coroutine D/​coroutine:​ start
 +2020-01-14 06:​24:​17.847 7602-7602/​com.nekotype.ips.coroutine D/​coroutine:​ end
 +2020-01-14 06:​24:​17.849 7602-7602/​com.nekotype.ips.coroutine D/​coroutine:​ coroutin
 +</​code>​
 +===== キャンセル =====
 +
 +<​code>​
 +    private var myjob:Job? =null
 +    private ​ var myjobs= mutableListOf<​Job?>​()
 +
 +    ...
 +        myjob=GlobalScope.launch {
 +            progress_countdown.max=1000
 +    ...
 +    ​
 +    // 画面を閉じた場合にコルーチンをキャンセル
 +    override fun onPause() {
 +        super.onPause()
 +        myjobs.map {
 +            Log.d("​choice","​cancel"​)
 +            it?​.cancel()
 +        }
 +    }
 +
 +</​code>​
 +
 +===== join =====
 +コルーチン内で他のコルーチンの終了を待機する。
 +
 +<code kotlin>
 +    fun TestCoroutin(){
 +        Log.d( ​ "​coroutine","​start"​)
 +        GlobalScope.launch() {
 +
 +            launch {
 +                Log.d( ​ "​coroutine","​coroutin_inner"​)
 +            }
 +
 +            Log.d( ​ "​coroutine","​coroutin_outer"​)
 +        }
 +        Log.d( ​ "​coroutine","​end"​)
 +    }
 +    ↓
 +2020-01-14 06:​29:​12.311 7952-7952/​com.nekotype.ips.coroutine D/​coroutine:​ start
 +2020-01-14 06:​29:​12.340 7952-7952/​com.nekotype.ips.coroutine D/​coroutine:​ end
 +2020-01-14 06:​29:​12.347 7952-7998/​com.nekotype.ips.coroutine D/​coroutine:​ coroutin_outer
 +2020-01-14 06:​29:​12.348 7952-7999/​com.nekotype.ips.coroutine D/​coroutine:​ coroutin_inner
 +</​code>​
 + ↓
 +<code kotlin>
 +    fun TestCoroutin(){
 +        Log.d( ​ "​coroutine","​start"​)
 +        GlobalScope.launch() {
 +
 +            launch {
 +                Log.d( ​ "​coroutine","​coroutin_inner"​)
 +            }.join() // 待つ
 +
 +            Log.d( ​ "​coroutine","​coroutin_outer"​)
 +        }
 +        Log.d( ​ "​coroutine","​end"​)
 +    }
 +    ↓
 +2020-01-14 06:​30:​51.472 8058-8058/​com.nekotype.ips.coroutine D/​coroutine:​ start
 +2020-01-14 06:​30:​51.500 8058-8058/​com.nekotype.ips.coroutine D/​coroutine:​ end
 +2020-01-14 06:​30:​51.505 8058-8111/​com.nekotype.ips.coroutine D/​coroutine:​ coroutin_inner //​順番が変わる
 +2020-01-14 06:​30:​51.508 8058-8110/​com.nekotype.ips.coroutine D/​coroutine:​ coroutin_outer //​順番が変わる
 +</​code>​
 +
 +
 +===== runBlockingとasync =====
 +runBlockingとasyncは戻り値をもつことができる。
 +asyncは非同期に処理する。asyncにはawaitでまつことができる。
 +
 +===== まとめ =====
 +
 +UIにアクセスするには
 +GlobalScope.launch(Dispatchers.Main) {...
 +
 +Jobを取得してキャンセルするには
 +myjob=GlobalScope.launch { ...
 +myjob.cancel()
 +
 +戻り値を取得するには
 +runBlocking
 +async
 +
 +待ちたいとき(同期)
 +GlobalScope.launch() {
 +launch { ... }.join() ​
 +
 +待ちたいとき(非同期) ​   ​
 +GlobalScope.launch() {
 +async { ... }.await() ​
kotlin/coroutines.1570864771.txt.gz · 最終更新: 2019/10/12 16:19 by ips