[解決済み】 java.lang.IllegalMonitorStateException: オブジェクトはwait()の前にスレッドによってロックされていない?)
質問
私は進行状況ダイアログを使用しています。私は、ユーザーが進行状況ダイアログを閉じたときにスレッドを停止する必要があります。残念ながらそれは例外pls私を与える。
内部クラスで
プレclass UpdateThread extends Thread{
public void run() {
while (true){
count=adapter.getCount();
try {
mHandler.post( new Runnable() {
public void run() {
Log.i(TAG,count+"count");
progressDialog.setMessage(count + "Device found");
}
});
Thread.sleep(300);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
オンクリーション
updateThread=new UpdateThread();
progressDialog= new ProgressDialog(GroupListActivity.this);
synchronized (this) {
updateThread.start();
}
解雇
progressDialog.setOnDismissListener(new DialogInterface.OnDismissListener() {
@Override
public void onDismiss(DialogInterface dialog) {
try {
synchronized (this) {
updateThread.wait(300);
}
} catch (InterruptedException e) {
e.printStackTrace();
}
Log.i(TAG,"Thread is stopped");
}
});
解決するには?
これは間違っています。
synchronized(foo) {
foo.wait();
}
問題は、このスレッドの目を覚まさせるものは何かということだ。 つまり、どうすれば
保証
を呼び出さないことを確認します。
{コード
以前
{を使用します。
最初のスレッドが
foo.notify()
? これは重要なことです。なぜなら、もしnotifyの呼び出しが先に起こると、fooオブジェクトはnotifyされたことを思い出さないからです。 もし notify() がひとつだけで、それが wait() よりも前に起こったなら、wait() は決して戻ってきません。
waitとnotifyの使い分けは、こんな感じです。
プレfoo.wait()
この例で最も重要なことは、条件に対する明示的なテスト(すなわち、q.peek() != null)があることと、ロックをかけずに誰も条件を変更しないことです。
もしコンシューマが最初に呼ばれたなら、キューが空であることがわかり、待つことになります。 生産者が忍び込んで、キューに製品を追加し、消費者がその通知を受け取る準備ができるまで、ロックを通知できる瞬間はないのです。
一方、producerが先に呼ばれた場合、consumerはwait()を呼ばないことが保証されています。
コンシューマでのループは2つの理由で重要である。 ひとつは、もし複数のコンシューマースレッドがある場合、あるコンシューマが通知を受け取った後、別のコンシューマがこっそりキューからProductを盗むことがあり得るということです。 このような場合、最初の消費者がする唯一の合理的なことは、次の商品を再び待つことです。 ループが重要であるもう一つの理由は、Javadocによると、オブジェクトが通知を受けていないときでもObject.wait()を返すことが許されていることです。 これは「スプリアスウェイクアップ」と呼ばれ、正しい処理方法は、戻ってもう一度待つことです。
また、注意点として、ロックは
private Queue<Product> q = ...;
private Object lock = new Object();
void produceSomething(...) {
Product p = reallyProduceSomething();
synchronized(lock) {
q.add(p);
lock.notify();
}
}
void consumeSomething(...) {
Product p = null;
synchronized(lock) {
while (q.peek() == null) {
lock.wait();
}
p = q.remove();
}
reallyConsume(p);
}
private
private
関連
-
[解決済み】Looper.prepare()を呼び出していないスレッド内でハンドラを作成できない。)
-
[解決済み】javaで指定されたファイルが見つからない
-
[解決済み】Javaの".class期待値"
-
[解決済み】Doubleはdereferencedできない?
-
[解決済み】Javaの部分文字列:「文字列のインデックスが範囲外」。
-
[解決済み】Javaでユーザー入力を待機させる方法
-
[解決済み】javaで無効な文字定数
-
[解決済み】Eclipseで「パッケージエクスプローラー」ビューが見つからない
-
[解決済み】クロススレッド操作が有効でない。作成されたスレッド以外のスレッドからアクセスされたコントロール
-
[解決済み] 現在のスレッドがメインスレッドでないことを確認する方法
最新
-
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 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み] if / for / while 内で "Missing return statement" が発生する。
-
[解決済み】代入の左手は必ず変数 CharAt
-
[解決済み】Android java.lang.IllegalStateException: Android java.lang.IllegalStateException: Could not execute method of the activity
-
[解決済み] java のクラス内のコンストラクタは、指定された型に適用できない
-
[解決済み] メソッドがスーパータイプのメソッドをオーバーライドまたは実装していない - Overrideの場合
-
[解決済み】Mockitoでモックからチェックされた例外を投げる
-
[解決済み】keytoolエラー 鍵屋が改ざんされたか、パスワードが不正確だった場合
-
[解決済み】Gradleがtools.jarを見つけ出さない
-
[解決済み】javaで無効な文字定数
-
[解決済み】フォルダに書き込もうとすると「java.nio.file.AccessDeniedException」が発生する件