According to Java Concurrency in Practice:
Timer is sensitive to changes in the system clock whereas ScheduledThreadPoolExecutor isn't.
Timer has just one execution thread, thus the long-running task tends to delay other tasks. While ScheduledThreadPoolExecutor can be configured with n number of threads. Moreover, you can have full control over created threads by providing ThreadFactory.
Runtime exceptions thrown in TimerTask will kill that one thread, thus making Timer dead. ScheduledThreadExecutor catches runtime exceptions and lets you handle them if you want by overriding afterExecute method from ThreadPoolExecutor. Only the task which threw exception will be canceled, but other tasks will continue to run.
I would suggest you use ScheduledThreadExecutor instead of Timer.
Also, note that ScheduledThreadExecutor is not available in Java 1.4 library, but there is a Backport of JSR 166 (java.util.concurrent) to Java 1.2, 1.3, 1.4, which has the ScheduledThreadExecutor class.