Kotlinで遅延後に関数を呼び出す方法は?


回答:


134

スケジュールを使用できます

inline fun Timer.schedule(
    delay: Long, 
    crossinline action: TimerTask.() -> Unit
): TimerTask (source)

例(@Nguyen Minh Binhに感謝-ここで見つけた:http ://jamie.mccrindle.org/2013/02/exploring-kotlin-standard-library-part-3.html )

import java.util.Timer
import kotlin.concurrent.schedule

Timer("SettingUp", false).schedule(500) { 
   doSomething()
}

16
ありがとう!超簡単。ここに例が見つかりましたjamie.mccrindle.org/2013/02/…– Timer("SettingUp", false).schedule(500) { doSomething() }
Nguyen Minh Binh

9
次の2つのインポートを追加した場合、コンパイルは行われます:import java.util.Timerおよびimport kotlin.concurrent.schedule
Customizer

3
@Matias Elorriaga、私にとって、これを新しいブランドファイルに置いてもコンパイルは行われず、インポートを追加してもカスタマイザが言った
Sulfkain

3
ファイルに置く必要はありません。そのメソッドはstdlibの一部です。回答の1行目のリンクをクリックしてください
Matias Elorriaga

3
kotlin.concurrent.scheduleKotlinは単に署名の不一致について不平を言っただけだったので、これはインポート後もコンパイルされないと当初思っていましたが、LongではなくIntを渡そうとしていることに気付きました。それを修正してまとめました。
Joe Lapp

178

使用するオプションもあります Handler -> postDelayed

 Handler().postDelayed({
                    //doSomethingHere()
                }, 1000)

18
質問は一般的なkotlinメソッドを要求するため、Androidでのみ利用可能であることを追加してください(Androidタグがあります)
Yoav Sternberg

5
それはあなたの側から建設的ではありません。その結果、ユーザーがandroidタグを検索すると、これは間違った答えであると考えられる可能性があります。
Bogdan Ustyak 2017

9
Androidの場合、それはタイマーよりもハンドラを使用することをお勧めします:stackoverflow.com/questions/20330355/timertask-or-handler
woprandi

アクティビティ/フラグメントの終了後にハンドラーを削除するためのコードを追加する必要があると思います。
CoolMind

これを行うつもりなら、これはUIスレッドでは実行されません。
AndroidDev

93

たくさんの方法

1. Handlerクラスの使用

Handler().postDelayed({
    TODO("Do something")
    }, 2000)

2. Timerクラスの使用

Timer().schedule(object : TimerTask() {
    override fun run() {
        TODO("Do something")
    }
}, 2000)

より短い

Timer().schedule(timerTask {
    TODO("Do something")
}, 2000)

最短

Timer().schedule(2000) {
    TODO("Do something")
}

3. Executorsクラスの使用

Executors.newSingleThreadScheduledExecutor().schedule({
    TODO("Do something")
}, 2, TimeUnit.SECONDS)

1
そして、あなたはここで最良の解決策は何だと思いますか?
Tamim Attafi

1
おそらく最初のハンドラーを使用します。stackoverflow.com/a/40339630/1159930を
Markymark

36

次の2つのライブラリをインポートする必要があります。

import java.util.*
import kotlin.concurrent.schedule

その後、次のように使用します。

Timer().schedule(10000){
    //do something
}

27

launchコルーチンを作成しdelayてから、関数を呼び出すことができます。

 /*GlobalScope.*/launch {
   delay(1000)
   yourFn()
 }

クラスまたはオブジェクトの外側にいる場合はGlobalScope、コルーチンをそこで実行させるためCoroutineScopeに追加します。それ以外の場合は、周囲のクラスにを実装して、必要に応じてそのスコープに関連付けられたすべてのコルーチンをキャンセルできるようにすることをお勧めします。


ありがとう!奇妙なことに、そのコルーチンは2018
。– CoolMind

@coolMind彼らは数ヶ月以来安定しているので、彼らは非常に新しいです...
ジョナスウィルムズ

はい、10月から11月までですが、以前は存在していました。
CoolMind

22
val timer = Timer()
timer.schedule(timerTask { nextScreen() }, 3000)

1
中かっこの代わりに「timerTask」を記述する必要がある理由を教えてください。
Hugo Passos 2017

2
そうだと思います。最初の引数としてTimer.schedule()a TimerTaskを期待します。kotlin.concurrent.timerTask()指定されたラムダをTimerTaskインスタンスでラップします。ここを参照してください:kotlinlang.org/api/latest/jvm/stdlib/kotlin.concurrent/...
Blieque

また、Timerオブジェクトを2回以上使用しない場合は、例のように1行に圧縮できますTimer().schedule(timerTask { ... }, 3000)。Kotlinに適したオプションも利用できます。jonguerの回答を参照してください。
ブリーク2018年

10

3秒後にトーストを表示する簡単な例:

fun onBtnClick() {
    val handler = Handler()
    handler.postDelayed({ showToast() }, 3000)
}

fun showToast(){
    Toast.makeText(context, "Its toast!", Toast.LENGTH_SHORT).show()
}

1
通話をキャンセルできますか?
Eduardo Oliveros

6

あなたが一般的な使用法を探しているなら、これが私の提案です:

次の名前のクラスを作成しますRun

class Run {
    companion object {
        fun after(delay: Long, process: () -> Unit) {
            Handler().postDelayed({
                process()
            }, delay)
        }
    }
}

そして、このように使用します:

Run.after(1000, {
    // print something useful etc.
})

これを拡張機能として簡略化できます
Vlad

@オグルカン、よりコトリニックなラムダRun.after(1000) { toRun() }。私は正しいですか
ビンレビン

0

SingleThreadは、使用後に強制終了する必要がないため、使用することをお勧めします。また、「stop()」メソッドはKotlin言語では非推奨になりました。

private fun mDoThisJob(){

    Executors.newSingleThreadScheduledExecutor().scheduleAtFixedRate({
        //TODO: You can write your periodical job here..!

    }, 1, 1, TimeUnit.SECONDS)
}

また、定期的な作業にもご利用いただけます。とても便利です。あなたが毎秒仕事をしたいなら、あなたはそのパラメータのために設定することができます:

Executors.newSingleThreadScheduledExecutor()。scheduleAtFixedRate(Runnable command、long initialDelay、long period、TimeUnit unit);

TimeUnitの値は、NANOSECONDS、MICROSECONDS、MILLISECONDS、SECONDS、MINUTES、HOURS、DAYSです。

@canerkaseler

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.