Upgrade to Pro — share decks privately, control downloads, hide ads and more …

夏のDispatchers.Main探検

 夏のDispatchers.Main探検

Kotlin Fest 2018でコルーチンの話をしてきた http://sys1yagi.hatenablog.com/entry/2018/08/28/000620
Androidと非同期処理 とCoroutine1.0.0 http://sys1yagi.hatenablog.com/entry/2018/12/19/104023
Android でコルーチン(パート I): 背景を理解する https://developers-jp.googleblog.com/2019/07/coroutines-on-android-part-i-getting-the-background.html
Android のコルーチン(パート II): 使ってみる https://developers-jp.googleblog.com/2019/07/coroutines-on-android-part-ii-getting-started.html
Android のコルーチン(パート III): 実際の処理 https://developers-jp.googleblog.com/2019/07/coroutines-on-android-part-iii-real-work.html
Job, CoroutineContext, CoroutineScopeなどを
整理したい https://speakerdeck.com/takahirom/job-coroutinecontext-coroutinescopenadowo-zheng-li-sitai
図で理解する Kotlin Coroutine https://qiita.com/kawmra/items/d024f9ab32ffe0604d39

Koji Wakamiya

August 15, 2019
Tweet

More Decks by Koji Wakamiya

Other Decks in Technology

Transcript

  1. 夏のDispatchers.Main探検
    Kotlin愛好会 vol.14 @ウォンテッドリー株式会社

    View Slide

  2. 自己紹介
    Name : Koji Wakamiya
    Work : Studyplus, inc.
    Github : @koji-1009
    Twitter : @D_R_1009
    Android開発メインでやってます
    2

    View Slide

  3. 今日の話のまとめ(TL;DR)
    3

    View Slide

  4. まとめ
    ● Dispatchers.MainはLooper.getMainLooper()を
    CoroutinesContextとして扱えるようにしたもの
    ● kotlinx.coroutinesパッケージと、kotlinx.coroutines.androidパッケージの
    組み合わせによりKotlin Coroutinesの世界とAndroidの世界が繋がれている
    ● R8によってDispatchres.Mainのinit処理が早くなった!!!
    4

    View Slide

  5. Kotlin Coroutinesのおさらい
    5

    View Slide

  6. Kotlin Coroutinesを理解するために
    ● Kotlin Coroutines
    ○ sys1yagiさんのブログ
    ■ Kotlin Fest 2018でコルーチンの話をしてきた
    ■ Androidと非同期処理 とCoroutine1.0.0
    ○ Googleのブログ
    ■ Android でコルーチン(パート I): 背景を理解する
    ■ Android のコルーチン(パート II): 使ってみる
    ■ Android のコルーチン(パート III): 実際の処理
    ● CoroutineContext
    ○ Job, CoroutineContext, CoroutineScopeなどを整理したい
    ○ 図で理解する Kotlin Coroutine
    6

    View Slide

  7. CoroutineDispatcher
    “Base class that shall be extended by all coroutine dispatcher implementations.”
    ● CoroutineDispatcherはCoroutineが実行環境を司る
    ○ 単一のスレッドだったり、スレッドプールだったり
    ○ 実行スケジュールだったり
    ● Dispatchersクラス経由でよくアクセスする
    Dispatcher
    ○ Dispatchers.Default
    ○ Dispatchers.IO
    ○ Dispatchers.Unconfined
    ○ Dispatchers.Main
    7

    View Slide

  8. Dispatchers.Main
    8

    View Slide

  9. Dispatchers.Mainとは
    “A coroutine dispatcher that is confined to the Main thread operating with UI objects. Usually such
    dispatchers are single-threaded.”
    ● UI操作のためにMainスレッド上で動作させるための
    Dispatcher
    ● プラットフォームごとに実装が異なる
    ○ JS/Native :Dispatchers.Defaultが指定
    ○ JVM :Android/JavaFX/Swingそれぞれのプラットフォーム拡張で対応
    9

    View Slide

  10. AndroidのDispatchers.Main
    Kotlin Coroutinesの実行をAndroidのHandler経由で実行させるクラス(モジュール)
    ● Looper.getMainLooper()したLooperに対するHandlerを生成することで
    Androidの仕組みを利用したMainスレッドへのアクセスを実現
    ● Android SDK 28から以上では Handler.createAsync (API 28で追加)を利用したHandlerに!
    10

    View Slide

  11. どうやってDispatchers.Mainを見つけるか
    ● JavaのServiceLoaderクラスを利用
    ○ ServiceLoaderはMETA-INFを利用することで、実装クラスを読み込む仕組み
    ● MainDispatcherLoader(kotlinx.coroutines.internal) が
    MainDispatcherFactory(kotlinx.coroutines.internal)を継承した
    AndroidDispatcherFactory(kotlinx.coroutines.android) を読み込む
    ● 独自のプラットフォームでも
    MainDispatcherFactoryを継承したクラスを作れば
    Kotlin CoroutinesのGUI対応ができる!!!
    11

    View Slide

  12. Dispatchers.Mainの
    R8による高速化
    12

    View Slide

  13. Dispatchers.Mainのinit処理時間問題
    13
    https://github.com/Kotlin/kotlinx.coroutines/issues/878

    View Slide

  14. なにが起きていたのか
    ● ServiceLoaderは使うべきではない……?
    14

    View Slide

  15. 対応
    15
    https://github.com/Kotlin/kotlinx.coroutines/pull/1304

    View Slide

  16. 対応
    ● R8 v1.6.0~で META-INF/com.android.tools 配下が rule として認識されるように
    ● META-INFが正しく認識されるようになるため、
    ServiceLoaderが正常に動作
    ○ ただしちゃんと動くのは Android Studio 3.6.0以上の模様
    16

    View Slide

  17. 今日の話のまとめ(再掲)
    17

    View Slide

  18. まとめ
    ● Dispatchers.MainはLooper.getMainLooper()を
    CoroutinesContextとして扱えるようにしたもの
    ● kotlinx.coroutinesパッケージと、kotlinx.coroutines.androidパッケージの
    組み合わせによりKotlin Coroutinesの世界とAndroidの世界が繋がれている
    ● R8によってDispatchres.Mainのinit処理が早くなった早くなる!!!
    いろんな非同期処理の ”Mainスレッド”について書いたブログ
    -> Androidの非同期処理について自分なりの整理
    18

    View Slide