Java Timer TimerTaskの例

Java java.util.Timer は、将来の特定の時点でスレッドを実行するようにスケジュールするために使用できるユーティリティクラスです。 Java Timer クラスは、一度だけ実行されるタスクまたは定期的な間隔で実行されるタスクをスケジュールするために使用できます。

Java TimerTask

java.util.TimerTask は、Runnable インターフェースを実装した 抽象クラス であり、このクラスを拡張して TimerTask を作成し、java Timer クラスを使用してスケジュールする必要があります。

Java Timer の例

JavaのTimerクラスはスレッドセーフであり、複数のスレッドが外部同期を必要とせずに単一のTimerオブジェクトを共有できます。Timerクラスは、指定された定期間隔でタスクを追加するためにjava.util.TaskQueueを使用し、いつでもTimerTaskを実行しているスレッドは1つだけであり、たとえば、タイマーを10秒ごとに実行するように設定しても、単一のスレッドの実行に20秒かかる場合、Timerオブジェクトはタスクをキューに追加し続け、1つのスレッドが終了するとキューに通知し、別のスレッドが実行を開始します。Java Timerクラスは、タスクをスケジュールするためにObject waitとnotifyメソッドを使用します。以下はJava TimerとTimerTaskの簡単なプログラムの例です。

package com.journaldev.threads;

import java.util.Date;
import java.util.Timer;
import java.util.TimerTask;

public class MyTimerTask extends TimerTask {

    @Override
    public void run() {
        System.out.println("Timer task started at:"+new Date());
        completeTask();
        System.out.println("Timer task finished at:"+new Date());
    }

    private void completeTask() {
        try {
            //タスクを完了するのに20秒かかると仮定
            Thread.sleep(20000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
    
    public static void main(String args[]){
        TimerTask timerTask = new MyTimerTask();
        //デーモンスレッドとしてタイマータスクを実行
        Timer timer = new Timer(true);
        timer.scheduleAtFixedRate(timerTask, 0, 10*1000);
        System.out.println("TimerTask started");
        //しばらくしてキャンセル
        try {
            Thread.sleep(120000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        timer.cancel();
        System.out.println("TimerTask cancelled");
        try {
            Thread.sleep(30000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }

}

1つのスレッドの実行に20秒かかりますが、Java Timerオブジェクトはタスクを10秒ごとに実行するようにスケジュールされていることに注意してください。以下はプログラムの出力です:

TimerTask started
Timer task started at:Wed Dec 26 19:16:39 PST 2012
Timer task finished at:Wed Dec 26 19:16:59 PST 2012
Timer task started at:Wed Dec 26 19:16:59 PST 2012
Timer task finished at:Wed Dec 26 19:17:19 PST 2012
Timer task started at:Wed Dec 26 19:17:19 PST 2012
Timer task finished at:Wed Dec 26 19:17:39 PST 2012
Timer task started at:Wed Dec 26 19:17:39 PST 2012
Timer task finished at:Wed Dec 26 19:17:59 PST 2012
Timer task started at:Wed Dec 26 19:17:59 PST 2012
Timer task finished at:Wed Dec 26 19:18:19 PST 2012
Timer task started at:Wed Dec 26 19:18:19 PST 2012
TimerTask cancelled
Timer task finished at:Wed Dec 26 19:18:39 PST 2012

出力は、タスクがすでに実行中である場合、タイマーはそれが終了するのを待ち、終了したらキューから次のタスクを開始します。JavaのTimerオブジェクトはデーモンスレッドとして関連するタスクを実行するために作成できます。Timer cancel() メソッドはタイマーを終了し、スケジュールされたタスクを破棄するために使用されますが、現在実行中のタスクには干渉せず、終了させます。タイマーが デーモンスレッド として実行されている場合、キャンセルしても、ユーザースレッドがすべて実行され終わるとすぐに終了します。Timerクラスにはタスクを特定の日付に一度だけ実行するためのいくつかの schedule() メソッドが含まれています。また、一定の間隔でタスクを定期的に実行するためのいくつかの scheduleAtFixedRate() メソッドもあります。Timerを使用してタスクをスケジュールする際には、通常のスレッド実行よりも時間間隔が長いことを確認する必要があります。そうでないと、タスクキューサイズが増え続け、最終的には常にタスクが実行されます。これでJava TimerとJava TimerTaskの簡単な概要が終わります。

Source:
https://www.digitalocean.com/community/tutorials/java-timer-timertask-example