0

いくつかの情報を相互に渡し、その情報を使用して後でコールバックしたいクラスがいくつかあります(コールバックパターン)。

私のアプリケーションでは、このメカニズムは2つの目的を果たします。

  • スケジュールされた/遅延した実行
  • メッセージングを含む非同期実行

私のオブジェクトは基本的に、「Xの実行が終了したら、電話をかけ直して、ZでYを実行するように指示します(それまでに忘れてしまったため)」とお互いに言います。Xが適切なタイミングを待っているだけでなく、リモートサービスと通信したり、ローカル関数を呼び出したりする場合。

さて、Javaに関数ポインタ(または同等のもの)があれば、1つと必要な引数を含む「Job」クラスを実装します。たとえば、PHPでは、この構造体にクラス名、関数名、および引数の配列を格納する必要があります。Cでは、これは関数へのポインターであり、すべての呼び出しで引数を同じ番号と型にする必要があります。

Javaでは、通常のアプローチは、次のように、コールバックしたいすべてのクラスによって実装されるインターフェースを持つことです。

public interface ICallable {
    public void call_me(Object data);
}

今、これは私にはうまくいきません。

  • コールバックされるオブジェクトには、呼び出しを受けるための異なるメソッドのセットがある場合があります
  • 発信者は、どの通話を行うべきかを決定する人ではありません

おそらく私の問題は、さまざまなコールバックに対して共通のデータ構造と呼び出しプロシージャを使用しようとしていることですが、原則として、それは私には理にかなっているようです。

Javaでこの状況にアプローチするための優れたデザインパターンは何ですか?

4

8 に答える 8

6

インターフェイスが最適なソリューションであることがわかると思います。彼らに対するあなたの反論が理解できません。受信者が別のメソッドを呼び出す必要がある場合は、Interface メソッドに別のメソッドを呼び出させます。

レシーバー クラスに複数のハンドラーが必要な場合は、必要なハンドラーの種類ごとに 1 つずつ、インターフェイスを実装する匿名の内部クラスを使用できます。たとえば、送信者が「ListenerInterface」と呼ばれるインターフェースを使用する場合、受信者は、ListenerInterface を実装し、受信者メソッド「handlerFunction」を呼び出す匿名の内部クラスを定義する場合があります。

   sender.addListener(new ListenerInterface()
   {
      public void callback(Object arg)
      {
         handlerFunction(arg);
      }
   });
于 2009-03-09T15:31:59.707 に答える
2

本当にインターフェイスを使用したくない場合 (そして私を信じてください!)、リフレクションを使用して呼び出したいメソッドを取得し、それを呼び出しを行う必要があるメソッドに渡すことができます。これは、取得しようとしている C 関数ポインターに限りなく近いものです。

リフレクションは、インターフェイスの方法よりも (おそらく) 遅くなります (ただし、頻繁に呼び出されない限り、問題にはなりません)。

リフレクションには、それを行うインターフェイスの方法にあるコンパイル時の型チェックがありません (つまり、実行時にクラッシュする可能性があります)。

リフレクションは、それを行うインターフェイスの方法よりも醜いコードになります。

しかし、本当に本当に C 関数ポインターをシミュレートしたいのであれば、リフレクションはあなたが得ようとしている限り近いものです。

于 2009-03-09T17:00:50.880 に答える
0

私は問題を誤解しているかもしれませんが、ある種のイベント システムをセットアップすることでメリットが得られるように思えます。

基本的に、イベント ハンドラーをセットアップし、イベントについて知りたいクラスをイベント ハンドラーにサブスクライブします。あなたの問題のために、Xが完了すると、オブジェクトがサブスクライブされる FinishedProcessingEvent() が発生します。オブジェクトがこのイベントを受け取ると (イベントを気にかけている他のサブスクライバーと共に)、適切なアクション (Y with Z) を実行します。これらのアクションはオブジェクト内で定義されるため、異なるオブジェクトは同じイベントに基づいて異なることを行うことができます。

これは役に立ちますか?

于 2009-03-09T15:30:55.823 に答える
0

あなたの問題を解決する興味深いパターンがあると確信していますが、インフラストラクチャを使用した単純なアプローチを選択します。要求と応答を JMS のようなメッセージ キューに詰め込むと、システムの再起動、永続性、メッセージの整合性を気にすることなく、数秒または数週間かかるイベントを処理できるため、システムがよりシンプルで堅牢になる可能性があります。

于 2009-03-09T15:32:06.197 に答える
0

私はあまり詳しく調べていませんが、Java 5+ Futureインターフェース (またはそのサブインターフェース) がこれに役立つかもしれません。

于 2009-03-09T15:34:03.477 に答える