[解決済み】JavaでThreadを正しく停止する方法は?
2022-03-30 22:01:41
質問
Javaでスレッドを適切に停止するためのソリューションが必要です。
私は
IndexProcessor
クラスは、Runnable インターフェースを実装しています。
public class IndexProcessor implements Runnable {
private static final Logger LOGGER = LoggerFactory.getLogger(IndexProcessor.class);
@Override
public void run() {
boolean run = true;
while (run) {
try {
LOGGER.debug("Sleeping...");
Thread.sleep((long) 15000);
LOGGER.debug("Processing");
} catch (InterruptedException e) {
LOGGER.error("Exception", e);
run = false;
}
}
}
}
そして、私は
ServletContextListener
クラスで、スレッドの開始と停止を行います。
public class SearchEngineContextListener implements ServletContextListener {
private static final Logger LOGGER = LoggerFactory.getLogger(SearchEngineContextListener.class);
private Thread thread = null;
@Override
public void contextInitialized(ServletContextEvent event) {
thread = new Thread(new IndexProcessor());
LOGGER.debug("Starting thread: " + thread);
thread.start();
LOGGER.debug("Background process successfully started.");
}
@Override
public void contextDestroyed(ServletContextEvent event) {
LOGGER.debug("Stopping thread: " + thread);
if (thread != null) {
thread.interrupt();
LOGGER.debug("Thread successfully stopped.");
}
}
}
しかし、tomcat をシャットダウンすると、IndexProcessor クラスで例外が発生します。
2012-06-09 17:04:50,671 [Thread-3] ERROR IndexProcessor Exception
java.lang.InterruptedException: sleep interrupted
at java.lang.Thread.sleep(Native Method)
at lt.ccl.searchengine.processor.IndexProcessor.run(IndexProcessor.java:22)
at java.lang.Thread.run(Unknown Source)
JDK1.6を使用しています。そこで質問です。
どうすれば、スレッドを停止して例外をスローしないようにできますか?
追伸
を使いたくありません。
.stop();
メソッドは非推奨だからです。
どのように解決するのですか?
において
IndexProcessor
クラスでは、スレッドが終了する必要があることを通知するフラグを設定する方法が必要です。
run
をクラススコープ内だけで使用しました。
スレッドを停止させたい場合は、このフラグをセットして
join()
を実行し、終了を待ちます。
volatile 変数を使用するか、フラグとして使用する変数と同期しているゲッターおよびセッターメソッドを使用して、フラグがスレッドセーフであることを確認します。
public class IndexProcessor implements Runnable {
private static final Logger LOGGER = LoggerFactory.getLogger(IndexProcessor.class);
private volatile boolean running = true;
public void terminate() {
running = false;
}
@Override
public void run() {
while (running) {
try {
LOGGER.debug("Sleeping...");
Thread.sleep((long) 15000);
LOGGER.debug("Processing");
} catch (InterruptedException e) {
LOGGER.error("Exception", e);
running = false;
}
}
}
}
次に
SearchEngineContextListener
:
public class SearchEngineContextListener implements ServletContextListener {
private static final Logger LOGGER = LoggerFactory.getLogger(SearchEngineContextListener.class);
private Thread thread = null;
private IndexProcessor runnable = null;
@Override
public void contextInitialized(ServletContextEvent event) {
runnable = new IndexProcessor();
thread = new Thread(runnable);
LOGGER.debug("Starting thread: " + thread);
thread.start();
LOGGER.debug("Background process successfully started.");
}
@Override
public void contextDestroyed(ServletContextEvent event) {
LOGGER.debug("Stopping thread: " + thread);
if (thread != null) {
runnable.terminate();
thread.join();
LOGGER.debug("Thread successfully stopped.");
}
}
}
関連
-
[解決済み] HashMapのtoString関数はなぜ異なる順序で自分自身を印刷するのですか?
-
[解決済み] java.util.concurrent.ExecutionException 例外をどのように処理しますか?
-
[解決済み] JavaでInputStreamを読み込んでStringに変換するにはどうすればよいですか?
-
[解決済み] JavaでNullPointerExceptionを回避する方法
-
[解決済み] JavaにおけるHashMapとHashtableの違いは何ですか?
-
[解決済み] Java Mapの各エントリを効率的に反復処理するには?
-
[解決済み] Javaでメモリーリークを発生させるにはどうしたらいいですか?
-
[解決済み] Javaにおけるpublic、protected、package-private、privateの違いは何ですか?
-
[解決済み] JavaでStringをintに変換するにはどうしたらいいですか?
-
[解決済み] Javaにおける "implements Runnable "と "extends Thread "の違いについて
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み] JavaでFileFilterを作るには?
-
[解決済み] コレクションへの共有参照が見つかりました org.hibernate.HibernateException
-
[解決済み] android.support.v4.app.FragmentActivity' で 'TAG' がプライベートアクセスされている。
-
[解決済み] javax.naming.NameNotFoundException
-
[解決済み] 1行目2列目でBEGIN_ARRAYを期待したが、BEGIN_OBJECTだった。
-
[解決済み] 午前0時からの時間を秒単位で取得する方法
-
[解決済み] HTTP ステータス 500 - サーブレットクラス pkg.coreServlet のインスタンス化に失敗しました。
-
[解決済み] JDBC タイプの方言マッピングがありません。1111
-
[解決済み] Mavenです。JARは空になります - 含有するためにマークされたコンテンツがありません
-
[解決済み] Maven: assembly-pluginが全く実行されない