java 如何在运行时更改 TimerTask 的执行周期?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/6520078/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-30 16:10:53  来源:igfitidea点击:

How can I change my TimerTask's execution period at runtime?I

javatimertimertask

提问by VextoR

How can I change period of Timer at runtime?

如何在运行时更改计时器的周期?

    Timer timer = new Timer();

    timer.scheduleAtFixedRate(new TimerTask() {
        public void run() {

             // read new period
             period = getPeriod();

             doSomething();

        }
    }, 0, period);

采纳答案by Mathias Schwarz

You cannot do this directly, but you can cancel the tasks on the Timerand reschedule them with the desired period.

您不能直接执行此操作,但您可以取消任务Timer并在所需时间段内重新安排它们。

There is no getPeriodmethod.

没有getPeriod方法。

回答by Bahramdun Adil

You can do it like this:

你可以这样做:

private int period= 1000; // ms

private void startTimer() {
    Timer timer = new Timer();
    timer.schedule(new TimerTask() {
        public void run() {
            // do something...
            System.out.println("period = " + period);
            period = 500;   // change the period time
            timer.cancel(); // cancel time
            startTimer();   // start the time again with a new period time
        }
    }, 0, period);
}

回答by Datz

You can use the following class to change the execution period of a TimerTaskat runtime.

您可以使用以下类TimerTask在运行时更改 a 的执行周期。

As already explained, it can not really change the period but has to cancel and reschedule the task:

如前所述,它不能真正改变时间段,但必须取消并重新安排任务:

import java.util.Objects;
import java.util.Timer;
import java.util.TimerTask;
import java.util.function.Supplier;

/**
 * {@link TimerTask} with modifiable execution period.
 * 
 * @author Datz
 */
public class EditablePeriodTimerTask extends TimerTask {

    private Runnable task;
    private Supplier<Long> period;
    private Long oldP;

    /**
     * Constructor with task and supplier for period
     * 
     * @param task the task to execute in {@link TimerTask#run()}
     * @param period a provider for the period between task executions
     */
    public EditablePeriodTimerTask(Runnable task, Supplier<Long> period) {
        super();
        Objects.requireNonNull(task);
        Objects.requireNonNull(period);
        this.task = task;
        this.period = period;
    }

    private EditablePeriodTimerTask(Runnable task, Supplier<Long> period, Long oldP) {
        this(task, period);
        this.oldP = oldP;
    }

    public final void updateTimer() {
        Long p = period.get();
        Objects.requireNonNull(p);
        if (oldP == null || !oldP.equals(p)) {
            System.out.println(String.format("Period set to: %d s", p / 1000));
            cancel();
            new Timer().schedule(new EditablePeriodTimerTask(task, period, p), p, p);
            // new Timer().scheduleAtFixedRate(new EditablePeriodTimerTask(task, period), p, p);
        }
    }

    @Override
    public void run() {
        task.run();
        updateTimer();
    }

}

The Timer can bes started like this:

定时器可以这样启动:

EditablePeriodTimerTask editableTimerTask =
    new EditablePeriodTimerTask(runnable, () -> getPeriod());
editableTimerTask.updateTimer();

Where runnableis your real task to be executed and getPeriod()provides the period between the task executions. Which of course can change depending on your requirements.

runnable您要执行的实际任务在哪里,并getPeriod()提供任务执行之间的时间间隔。当然可以根据您的要求进行更改。