3

参考までに、Swing on Java の GUI にメディエーター パターンを採用しました。

残念ながら、ユーザー入力が新しいウィンドウを必要とする場合、同時変更例外が常にスローされます。

これは、私のコードが、既存の同僚 (ウィンドウ) からのユーザー入力を処理する過程で、メディエーターの同僚のリストに新しい同僚 (新しいウィンドウ) を追加しようとするためです。

例えば

public MainScreenColleague implements GuiColleague, ActionListener {
    private GuiMediator mediator;
    public MainScreenColleague(GuiMediator medi) {
        mediator = medi;
        // implement JFrame with JButtons
    }
    public conveyInputToMediator(EventObject event) {
        mediator.conveyInputToColleagues(event);
    }
    public receiveInputFromMediator(EventObject event) {
        if (event.getSource() = particularBtn) {
            GuiColleague particularColleague = new ParticularConcreteColleague(mediator);
            //THIS IS THE CODE THAT THROWS CONCURRENCY EXCEPTION
            mediator.addGuiColleague(particularColleague);
        }       
}

私が採用できる新しい同僚の追加を処理するための他の構造はありますか? 提案やアイデアをお寄せいただきありがとうございます。

4

2 に答える 2

1

1つのオプションは、Swing風のモデルを採用し、メディエーターに、適切なタイミングで行う必要のある更新の「イベントキュー」を保存させることです。そうすれば、他のオブジェクトからのイベントを処理しているときに新しいウィンドウを追加するときに、そのウィンドウがロジックを混乱させることはありません。メディエーションが完了した後に処理される「完了時にこれを処理する」キューに追加されるだけです。

もう1つのオプションは、反復する前にリストのコピーを作成することです。これにより、反復中に生の構造に加えられた変更が、反復されるリストに表示されなくなります。

さらに別のアイデアは、要素を訪問するためにいくつかの非イテレータ手法を使用することです。たとえば、ウィンドウをリストに保存している場合は、次のようなforループを使用できます。

for (int i = 0; i < elems.size(); ++i)
    /* ... */

これらの種類の例外はスローされません。

于 2011-02-04T23:36:21.120 に答える
1

トラバーサルの数が変更の数をはるかに上回る場合、 CopyOnWriteArrayListのようなコピー オン ライト データ構造が適している可能性があります。

于 2011-02-04T23:48:36.523 に答える