Java – Reinitialize fix delay in ScheduledExecutorService

javajava.util.concurrent

As per my requirement, I have to execute some particular code after certain period of time. To do the same I have chose ScheduledExecutorService.scheduleWithFixedDelay(runnable, 0, 5, TimeUnit.SECONDS) and it's working fine for me. But according to my another requirement, the time mentioned in fixedDelay should be configurable at runtime. Means, currently total Delay is 5 seconds but latter if user want then can change the time into 60 seconds and in runtime fixedDelay will run after 60 seconds. Any help would be appreciable.

Please see the code:

static int i = 0;
    static ScheduledExecutorService executor;
    static Runnable runnable;
    static ScheduledFuture<?> future;

    public static void main(String args[]) {
        executor = Executors
                .newScheduledThreadPool(1);
        runnable = new Runnable() {
            @Override
            public void run() {
                System.out.println("Inside runnable" + i++);
                changeDelay();
            }
        };
        future =
                executor.scheduleWithFixedDelay(runnable, 0, 5, TimeUnit.SECONDS);

    }

    public static void changeDelay() {
        future.cancel(false);
        future = executor.scheduleWithFixedDelay(runnable, 0, 10, TimeUnit.SECONDS);
    }

Here I have used changeDelay method to change the delay time. But it's not working.

Best Solution

You need to keep the reference of the returned ScheduledFuture<?> object:

ScheduledFuture<?> handle =
       scheduler.scheduleWithFixedDelay(runnable, 0, 5, TimeUnit.SECONDS);

With this reference you cancel the current task and create another one with the new delay:

handle.cancel(false);    
handle = scheduler.scheduleWithFixedDelay(runnable, 0, 60, TimeUnit.SECONDS);

Here is an example:

public class Test5 {
    static int i = 0;
    static ScheduledExecutorService executor;
    static Runnable runnable;
    static ScheduledFuture<?> future;

    public static void main(String args[]) throws InterruptedException{
        executor = Executors.newScheduledThreadPool(1);
        runnable = new Runnable() {
            @Override
            public void run() {
                System.out.println("Inside runnable" + i++);
            }
        };
        future = executor.scheduleWithFixedDelay(runnable, 0, 5, TimeUnit.SECONDS);

        Thread.sleep(20000l);

        changeDelay();
    }

    public static void changeDelay() {
        boolean res = future.cancel(false);

        System.out.println("Previous task canceled: " + res);

        future = executor.scheduleWithFixedDelay(runnable, 0, 20, TimeUnit.SECONDS);
    }
}