【问题标题】:print a line for the firstt time and then every 30 minutes第一次打印一行,然后每 30 分钟打印一次
【发布时间】:2016-02-05 06:01:51
【问题描述】:

我有一个下面的方法,它将每隔一分钟从后台线程调用一次。

public void testMethod() {
    // some other code

    System.out.println("hello")

    // some other code
}

现在每隔一分钟,hello 行就会被打印出来。有什么办法,第一次打印 hello 行,然后在后台线程调用 testMethod 后每半小时(不一定是半小时)打印一次。我不想使用任何执行程序或计时器类。

我只是不希望我的 hello 行每分钟打印一次。在开始时它应该打印一次,然后每 30-35 分钟就可以了。有没有其他方法可以在不使用 Timer 或 Executors 的情况下做到这一点?我们可以不使用当前时间并进行一些 mod 检查吗?

我希望 testMethod 中的所有其他代码每分钟执行一次,这样我就无法睡觉或任何事情。我只需要进行一些随机检查,我们可以通过它来决定是否打印 hello。我只是不想每分钟打印一次 hello。

【问题讨论】:

  • 您希望程序何时停止打印?还是您希望它在没有结束时间的情况下运行?
  • 是的,保持原样运行。每当我调用 testMethod 的后台线程停止时,它最终都会停止。
  • 请解释为什么不能使用计时器。您描述的情况 screams 计时器;为什么要逆势而为?
  • @user1950349,我已根据您更新的问题和 cmets 更新了我的答案

标签: java date for-loop iteration


【解决方案1】:

有一个用于停止循环的静态成员变量

private static boolean isTrue = true;

public static boolean getIsTrue() {
    return isTrue;
}

public static void setIsTrue(boolean test) {
    YourClass.isTrue = test;
}

你的程序应该是

    System.out.println("hello");
    Thread printText = new Thread(){
        public void run() {
            while(getIsTrue()) {
                try {
                    Thread.sleep(30*60*1000);
                } catch (InterruptedException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
                System.out.println("hello");
            }
        }
    };
    printText.start();

当你想停止循环时

public void testMethod() {
    setIsTrue(false);
}

【讨论】:

  • @ChiefTwoPencils,重新检查您的否决票,我更新的答案在不同的线程中执行打印部分,以便可以执行其余代码。基于这个问题,我认为我的回答是有效的。
  • 我现在已恢复投票。归根结底,我认为睡眠并不优于其他选择,但 OP 有一些可疑的要求,所以我不会反对你。
  • 是的,同意。我本来想建议Scheduler
【解决方案2】:

正如您所说,您是从后台线程调用它,您可以使用无限循环或有限循环并在其中添加Thread.sleep(30*60*1000)

如果你想让它无限循环

public void testMethod() {
    (new Thread() {
        public void run() {
            long unixTime = System.currentTimeMillis() / 1000L;
            while(true){
                long currentUnixTime = System.currentTimeMillis() / 1000L;
                if ((currentUnixTime - unixTime)>=30*60){
                    System.out.println("hello");
                    unixTime = currentUnixTime;
                }
            }
        }
   }).start();
}

这个实现会浪费很多你的cpu周期,你可以用同样的逻辑来实现一个有限的。

【讨论】:

  • 我不想一直等待 30 分钟...我希望 testMethod 中的所有其他东西都按原样工作.. 只是一些随机检查,我们将决定是否打印 hello。如果条件不满足,则在 testMethod 中执行其他操作
  • @user1950349 然后从另一个专门用于此工作的后台线程调用此方法
【解决方案3】:

在我看来,问题不是要睡半个小时。问题说除非至少经过半小时,否则应该跳过方法的一部分。

在 Java 8 及更高版本中,您应该使用 java.time 框架进行日期时间工作。我们只需要 Instant 类,它代表 UTC 时间线上的一个时刻。

将下一次需要执行的额外代码存储在java.time.Instant 类型的变量中。初始化到刚才,这样额外的代码将在第一次运行。

Instant instantWhenDue = Instant.now().minusSeconds( 1 );

在您的方法中添加一个测试以查看当前时刻是否超过了我们的预定时间。

// do some stuff…
if ( Instant.now().isAfter( instantWhenDue ) ) {
    // do your extra work like say Hello…
    // Set when due to run again.
    instantWhenDue = Instant.now().plusMinutes( 30 );
}
// do other stuff…

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-01-30
    • 1970-01-01
    • 2016-10-26
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多