1

私は、Java をブラッシュアップする練習として小さなコンソール アプリケーションを作成しています (昨年は Java を 1 年間使用した後、Haskell と Scala を使用していました)。メニューの動作をモデリングする次のインターフェイスがあります。

public interface MenuItem {
    public String output();
    public InputHandler requestInput();

と:

public interface InputHandler {
    public String promptUser();
    public MenuItem handleInput(String input);
}

次のようないくつかのサンプル実装を使用します。

public class MainMenu implements MenuItem {

    public String output() {
        return "1.) Browse Books\n" +
               "2.) View membership details\n" +
               "3.) Exit\n";
    }

    public InputHandler requestInput() {
        return new InputHandler() {
            public String promptUser() {
                return "Please select an option:\n";
            }

            public MenuItem handleInput(String input) {
                int menuItem = Integer.parseInt(input);
                if (menuItem == 1) {
                    return new BrowseBooks();
                } else if (menuItem == 2) {
                    return new ViewUserDetails();
                } else {
                    return new MainMenu();
                }
            }
        };
    }
}

私の問題は、これらのMenuItem実装クラスの一部 (BrowseBooksMenuたとえば、) が他のクラス (つまりLibraryManager、本の借用を処理するクラス) へのアクセスを必要とすることです。LibraryManagerこのクラスをクラスに渡すことはできません。クラスBrowseBooksにも渡す必要があるMainMenuため (それらは一種の循環であるため)、特定の MenuItem でのみ使用されるインスタンスの大きなコンストラクターの大きな混乱になります。

これを解決する良い方法は何ですか?

4

3 に答える 3

2

解決策として依存性注入を検討することをお勧めします。このような状況でサービスの依存関係を管理するのに最適です。GuiceWeldPicoContainerなどの優れたスタンドアロン DI 実装がいくつかあります。

于 2013-01-23T06:22:01.910 に答える
1

クラスにも渡す必要があるためLibraryManager、このクラスをクラスに渡すことはできません(一種の循環であるため)BrowseBooksMainMenu

これを構築するために何が必要かによって異なりますLibraryManager。何も必要ない場合は、BrowseBooksクラス内から単純に構築できます。グローバル構成が必要な場合は、グローバル シングルトンを構築し、それを静的フィールドに格納できます。Java のシングルトン デザイン パターンに関する回答には、初期化を早期に行うか遅延的に行うかに応じて、シングルトンを初期化する方法に関するコード スニペットがあります。

そのマネージャーがどこから来たのかについて柔軟にしたい場合は、おそらくInversion of Control Containerを使用して、依存性注入を見たいと思うかもしれません。

于 2013-01-23T06:25:40.143 に答える
0

デザインパターンを使用するだけで解決でき、DIシステムを使用する必要はありません。

これがあなたのために働くと私が思う簡単なコードプロトタイプであり、あなたのLybraryManagerと他のクラスの間の依存関係を取り除きます。

//LybraryManager singleton class
        public class LybraryManager{

    public static LybraryManager getInstance(){    //basic code for singleton pattern }

    public void addLybraryManagerListener(LMListener listener){    listneres.add(listener) }

    public void someLybraryOperation(){
         //iterate by the listeners and invoke the method
         listener.someLybraryOperationExecuted(someParam); }


    public interface LMListener{
         public void someLybraryOperationExecuted(Object someParam);
    }

//Class MainMenu that implement listener for lybrarymanager, and listen to operation
public class MainMenu implements LMListner {
    public MainMenu(){
        LybraryManager.getInstance.addLMListener(this);
}

public void someLybraryOperationExecuted(Object someParam){
    //do anything you need
}

}

私はそれがあなたの問題を解決することを願っています:)

于 2013-01-23T06:40:05.683 に答える