Task Scheduling
Code: reminder.java
import java.util.Timer;
import java.util.TimerTask;
/**
* Simple demo that uses java.util.Timer to schedule a task
* to execute once 5 seconds have passed.
*/
public class Reminder {
Timer timer;
public Reminder(int seconds) {
timer = new Timer();
timer.schedule(new RemindTask(), seconds*1000);
}
class RemindTask extends TimerTask {
public void run() {
System.out.println("Time's up!");
timer.cancel(); //Terminate the timer thread
}
}
public static void main(String args[]) {
new Reminder(5);
System.out.println("Task scheduled.");
}
}
Stopping Timer Threads
There are four ways that you can stop a timer:
- Invoke
cancel
on the timer. You can do this from anywhere in the program, such as from a timer task抯run
method. - Make the timer抯 thread a 揹aemon? by creating the timer like this:
new Timer(true)
. If the only threads left in the program are daemon threads, the program exits. - After all the timer抯 scheduled tasks have finished executing, remove all references to the
Timer
object. Eventually, the timer抯 thread will terminate. - Invoke the
System.exit
method, which makes the entire program (and all its threads) exit.
Performing a Task Repeatedly
This can be accomplished by changing a different timer.schedule(); Here are all the schedule APIs that can be used to performe a task repeatedly schedule(TimerTask task, long delay, long period)
schedule(TimerTask task, Date time, long period)
scheduleAtFixedRate(TimerTask task, long delay, long period)
scheduleAtFixedRate(TimerTask task, Date firstTime, long period)
Implementing the Runnable Interface
You have now seen two ways to provide therun
method.- Subclass the
Thread
class and override therun
method. See theSimpleThread
class described in the section Subclassing Thread and Overriding run. - Provide a class that implements the
Runnable
interface and therefore implements therun
method. In this case, aRunnable
object provides therun
method to the thread. See theClock
applet in the preceding section.
There are good reasons for choosing either of these options over the other. However, for most cases, including that of the
Clock
applet, if your class must subclass some other class (the most common example beingApplet
), you should useRunnable
.import java.awt.Graphics; import java.util.*; import java.text.DateFormat; import java.applet.Applet; public class Clock extends Applet implements Runnable { private Thread clockThread = null; public void start() { if (clockThread == null) { clockThread = new Thread(this, "Clock"); clockThread.start(); } } public void run() { Thread myThread = Thread.currentThread(); while (clockThread == myThread) { repaint(); try { Thread.sleep(1000); } catch (InterruptedException e) { //the VM doesn抰 want us to sleep anymore, //so get back to work } } } public void paint(Graphics g) { //get the time and convert it to a date Calendar cal = Calendar.getInstance(); Date date = cal.getTime(); //format it and display it DateFormat dateFormatter = DateFormat.getTimeInstance(); g.drawString(dateFormatter.format(date), 5, 10); } //overrides Applet抯 stop method, not Thread抯 public void stop() { clockThread = null; } }
- Subclass the