10

ここで Vaadin コードが頻繁にブロックされますが、何が問題なのかわかりません。

Thread 7892: (state = IN_JAVA)
 - java.util.HashMap.getEntry(java.lang.Object) @bci=61, line=349 (Compiled frame; information may be imprecise)
 - java.util.HashMap.containsKey(java.lang.Object) @bci=2, line=335 (Compiled frame)
 - java.util.HashSet.contains(java.lang.Object) @bci=5, line=184 (Compiled frame)
 - com.vaadin.ui.Table.unregisterPropertiesAndComponents(java.util.HashSet, java.util.HashSet) @bci=85, line=1693 (Compiled frame)
 - com.vaadin.ui.Table.refreshRenderedCells() @bci=992, line=1641 (Compiled frame)
 - com.vaadin.ui.Table.valueChange(com.vaadin.data.Property$ValueChangeEvent) @bci=23, line=2897 (Compiled frame)
 - com.vaadin.data.util.IndexedContainer.firePropertyValueChange(com.vaadin.data.util.IndexedContainer$IndexedContainerProperty) @bci=140, line=553 (Compiled frame)
 - com.vaadin.data.util.IndexedContainer.access$1000(com.vaadin.data.util.IndexedContainer, com.vaadin.data.util.IndexedContainer$IndexedContainerProperty) @bci=2, line=64 (Compiled frame)
 - com.vaadin.data.util.IndexedContainer$IndexedContainerProperty.setValue(java.lang.Object) @bci=202, line=915 (Compiled frame)
 - com.aimprosoft.wavilon.backgroundthreads.ChangeCdrThread.insertNewPersonIntoTable(com.aimprosoft.wavilon.model.Person, com.vaadin.ui.HorizontalLayout, com.aimprosoft.wavilon.ui.menuitems.CallContent, com.vaadin.ui.Table) @bci=924, line=208 (Interpreted frame)
 - com.aimprosoft.wavilon.backgroundthreads.ChangeCdrThread$RepaintTableThread.run() @bci=622, line=446 (Compiled frame)

誰かがこの問題をさらにデバッグする方法を提案できますか? この問題はめったに発生せず、再現するのは非常に困難です。

4

3 に答える 3

17

コード内のどこにあるかに基づいて、私が考えることができる唯一の説明は、HashMap適切に同期せずにそれにアクセスして更新する複数のスレッドがあるということです。これにより、マップのデータ構造が破損し、無限ループが発生する可能性があります。

java.util.HashMap.getEntryブロックする理由は他に考えられません。同期やI/Oは行いません。


Roland Illigのコメント:

行番号は確かに、コードがe = e.nextループの1つでハングしていることを示しています。

それは私の仮説を支持します。2つ(またはそれ以上)のスレッドによって実行されるハッシュテーブルに対する特定の一連の操作により、ハッシュチェーンの1つにループ/サイクルが作成されました。この破損は、操作を実行するスレッド間の同期が不十分だったために発生しました。それはめったに起こらないようなことですが、一度起こったら腐敗は消えません。

Vaadinのソースコードを詳しく調べないと、それがVaadinのバグなのか、Vaadinの使用方法のバグなのかを正確に知ることはできません。どちらの説明ももっともらしいです。

アップデート

この記事(以下のコメントで提供)に基づいて、アプリケーションが同期している(または同期していない)方法に問題がある可能性が高いと言えます。

于 2012-04-18T23:53:24.987 に答える
9

つまり、ここで実際に見ているのは、評価する無限ループに入るスレッドです。e = e.next

本質的に

e.next == e

これは、テーブルの再構築中に複数のスレッドによってHashMapに入れている場合に発生します。

詳細については、このリンクをご覧ください

美しい競合状態

これを解決するには、Collections.synchronizedMapまたはを使用しConcurrentHashMapます。後者をお勧めします。

于 2012-04-19T20:51:41.483 に答える
2

コンポーネントを変更するときに、バックグラウンド スレッドはアプリケーション インスタンスで同期されていますか? そうでない場合、それはあなたの問題です。

于 2012-04-19T20:37:34.270 に答える