SwingWorkerは、Javaプログラミング言語のSwingライブラリ用にSun Microsystemsが開発したユーティリティクラスです。SwingWorkerはイベントディスパッチスレッドを適切に使用できるようにします。Java 6以降、SwingWorkerはJREに含まれています。[1]
1998 年から 2006 年にかけて、互換性のない非公式の SwingWorker バージョンがいくつか作成されました。Java 6 より前のこれらのバージョンに関する大量のドキュメントを避けるように注意する必要があります。
Java 6.0 での使用
イベントディスパッチスレッドの問題
SwingWorker は、ユーザー インタラクション イベント (たとえば、JButton を押して巨大な XML ファイルを解析する) の後に時間のかかるタスクを実行する必要がある場合に便利です。最も簡単な方法は次のとおりです。
private Document doc ; ... JButton button = new JButton ( "Open XML" ); button . addActionListener ( new ActionListener () { @Override public void actionPerformed ( ActionEvent e ) { doc = loadXML (); } } );
これは機能しますが、残念ながら、メソッドはメインの Swing スレッド (イベント ディスパッチ スレッド) と同じスレッドloadXML()で呼び出されるため、メソッドの実行に時間が必要な場合、その間
GUI はフリーズします。
SwingWorker ソリューション
この問題は Java に固有のものではなく、多くのGUIモデルに共通しています。SwingWorker時間のかかるタスクを別のバックグラウンド スレッドで実行し、その間
GUI の応答性を維持することで、この問題を解決する方法を提案しています。
ワーカーの作成
次のコードは、メソッド呼び出しをカプセル化する SwingWorker を定義しますloadXML()。
SwingWorkerワーカー= new SwingWorker < Document , Void > () { @Override public Document doInBackground () { Document intDoc = loadXML (); return intDoc ; } };
ワーカーの実行
メソッドを使用して実行を開始します
SwingWorker.execute()。
結果の取得
メソッドを使用して結果を取得できますSwingWorker.get()。
get()イベント ディスパッチ スレッドを呼び出すと、タスクが完了するまで再描画を含むすべてのイベントの処理がブロックされるため、時間のかかる操作が完了する前に呼び出すことは避ける必要があります。タスク完了
後に結果を取得するには、次の2 つの方法があります。
- メソッドをオーバーライドします
SwingWorker.done()。このメソッドは、メイン イベント ディスパッチ スレッドで呼び出されます。
private Document doc ; ... SwingWorker < Document , Void > worker = new SwingWorker < Document , Void > () { @Override public Document doInBackground () { Document intDoc = loadXML (); return intDoc ; } @Override public void done () { try { doc = get (); } catch ( InterruptedException ex ) { ex . printStackTrace (); } catch ( ExecutionException ex ) { ex . printStackTrace (); } } }
- ワーカー メソッドを使用してリスナーを登録します
SwingWorker.addPropertyChangeListener(PropertyChangeListener)。リスナーにはワーカーの状態の変化が通知されます。
完全なワーカーの例
private Document doc ; ... JButton button = new JButton ( "Open XML" ); button . addActionListener ( new ActionListener () { @Override public void actionPerformed ( ActionEvent e ) { SwingWorker < Document , Void > worker = new SwingWorker < Document , Void > () {
@Override
public Document doInBackground () { Document intDoc = loadXML (); return intDoc ; } @Override public void done () { try { doc = get ( ); } catch ( InterruptedException ex ) { ex.printStackTrace ( ) ; } catch ( ExecutionException ex ) { ex.printStackTrace (); } } }; worker.execute ( ); } } ) ;
履歴: Java 6.0 以前の使用法
SwingWorker は Java 6.0 以降、Java SE の一部となっています。Sun は以前の JDK で使用するためのバージョンをリリースしていますが、それらは非公式バージョンであり、Java SE の一部ではなく、標準ライブラリのドキュメントにも記載されていませんでした。[2]これらのバージョンの最新版は 2003 年のものであり、SwingWorker バージョン 3 と呼ばれることがよくあります。 [3]残念ながら、JDK 6.0 SwingWorker とバージョン 3 SwingWorker は異なるメソッド名を使用しており、互換性がありません。現在、Java 6 より前のバージョンでは、バックポート バージョン (以下を参照) の使用が推奨されています。
SwingWorker 3 をインスタンス化する例を以下に示します。
SwingWorker worker = new SwingWorker () { public Objectconstruct () { ... // バックグラウンド スレッドのコードを追加します} public void finished () { ... // ここで追加したコードは UI スレッドで実行されます} }; worker . start (); // バックグラウンド スレッドを開始します
このstart()メソッドは、別のスレッドで、construct() メソッドに追加されたコードを実行します。バックグラウンド スレッドが終了したときに通知するには、finished()メソッドをオーバーライドするだけです。このconstruct()メソッドは、後で SwingWorker のメソッドを使用して取得できる結果を返すことができますget()。
Java 6 SwingWorker のバックポート
Java 6 SwingWorker の Java 5 へのバックポートは、http://swingworker.java.net/ [ permanent dead link ]で入手できます。パッケージ名 ( org.jdesktop.swingworker) を除けば、Java 6 SwingWorker と互換性があります。
同等物
System.ComponentModel.BackgroundWorker- .NET フレームワークflash.system.Worker-アドビフラッシュandroid.os.AsyncTask-アンドロイド
参考文献
- ^
SwingWorker - ^ J2SE 6.0 以前と以後のパッケージ概要を参照してください
javax.swing。また、バージョン 6.0 までは、ドキュメントのインデックス ページに SwingWorker クラスがリストされていないことに注意してください: [1]、[2]。 - ^ 「SwingWorker 3」をダウンロードできます。インターネットアーカイブ。2012年6月26日時点のオリジナルよりアーカイブ。
外部リンク
- Java 7 の SwingWorker クラスのドキュメント。
- Oracle の Swing での Java 並行性チュートリアルのワーカー スレッドと SwingWorker。
- Java SE 6 で SwingWorker を使用してアプリケーション パフォーマンスを向上させる (John O'Conner、2007 年 1 月)。
