1

を使用しScheduledExecutorServiceて、固定レートでタスクを実行します。これが私のメインメソッドの内容です:

RemoteSync updater = new RemoteSync(config);
try  {
    updater.initialise();
    updater.startService(totalTime, TimeUnit.MINUTES);
} catch (Exception e) {
    e.printStackTrace();
}

RemoteSyncAutoCloseableは(and Runnable) インターフェイスを実装しているため、最初はtry-with-resources次のように を使用しました。

try (RemoteSync updater = new RemoteSync(config)) {
    ...
} catch (Exception e) {
   e.printStackTrace();
}

ただしupdater.startService()、タスクをスケジュールした直後に戻るため、updater.close()が途中で呼び出され、アプリケーションが終了します。

startService()方法は次のRemoteSyncとおりです。

public void startService(int rate, TimeUnit unit) {
    ScheduledExecutorService scheduledExecutorService = Executors.newScheduledThreadPool(1);
    service =
        scheduledExecutorService.scheduleWithFixedDelay(this, 1L,
        rate,
        unit);
}

理想的には、次のような方法が必要です。

scheduledExecutorService.executeAtTermination(Runnable task)

これにより、スケジューラが実際に停止したときに呼び出すことができますclose()が、残念ながら私はそのような方法を知りません。

私ができることは、次のstartService()ような方法でメソッドをブロックすることです:

while (!scheduledExecutorService.isTerminated()) {
    Thread.sleep(10000);
}

しかし、これは汚くてハックな気がします。

どんな提案でも大歓迎です。

4

2 に答える 2

1

おそらく、アプリケーションのシャットダウンフックを使用できます。この議論のように。

アプリケーションの初期化のある段階で、次のようなコードを追加できます。

Runtime.getRuntime().addShutdownHook(new Thread() {
  public void run() {
    >>> shutdown your service here <<<
  }
});
于 2015-05-14T11:44:08.497 に答える
0

scheduledExecutorService.awaitTermination(Long.MAX_VALUE, TimeUnit.MILLISECONDS),おそらく別のスレッドで試すことができます

于 2015-05-07T12:57:29.980 に答える