1

IoC、DIP、DI、Service Locators に関するさまざまな記事を読みましたが、少し混乱しています。これは、いくつかの記事にはあまりにもあいまいな例があり、他の記事には他のケースについて言及せずに特定の例だけが含まれているためです。

以下の例を見て、どの例がどのパターンに一致するかを簡単に説明してください。

  • インターフェイスをコンストラクターに手動で渡す:

    class Consumer
    {
      public Consumer(IStore store){...}
    }
    ...
    
    Consumer c = new Consumer(new ConcreteStore());
    
  • 最初の例と同じですが、サードパーティのライブラリ (Unity、Windsor、Ninject) を使用しています

  • 最初の例と同じですが、IStore インターフェイスの代わりに BaseStore クラスを使用しています

  • コンストラクターではなく、他のメソッドに依存関係を渡します。

    class Consumer
    {
      public BySomething(IStore store){...}
    }
    ...
    
    Consumer c = new Consumer();
    c.BySomething(new ConcreteStore());
    
  • 他のインターフェイス内でマスクされた依存関係を渡す (このソリューションのボーナス - 「世界」で他のものが発明され、消費者がそれらを使用したい場合、コンストラクターの引数を変更する必要はなく、IWorld を更新するだけです。完全にテスト時にワールド全体を別のものに置き換えます):

    interface IWorld
    {
      IDictionary<string,IStore> Stores { get; set; }
      IDictionary<string,ICityMap> Maps { get; set; }
      ...
    }
    
    class Consumer
    {
      public Consumer(IWorld world){...}
      public BySomething(string store, string city){...}
    }
    
    ...
    
    IWorld myWorld = new HeavenlyWorld();
    ... // adding stores, maps and whatnot
    
    Consumer c = new Consumer(myWorld);
    

    サブ質問: この場合、IWorld はサービス ロケーターですか、それとも正確ではありませんか?

  • コールバック関数またはデリゲート (この場合は .NET アクション) を渡します。

    c.BySomething(store, city, new Action(() => {...} ));
    

    このケースを追加したのは、 Inversion of Controlの記事で、すべてのコールバックが IoC であると述べられているためです。本当ですか?

4

2 に答える 2

1

コンストラクター/メソッドの引数として依存関係を渡すたびに、それが依存性注入です。ほとんどの例のように手動で行うことも、IoC コンテナーとして知られる DI コンテナーを使用して自動で行うこともできます。

コンテナーを使用するということは、dep を使用するオブジェクトがコンテナーによって構築されることを意味します。そのサービスをコンテナーに直接要求することができます。その場合、そのサービスを公開する静的プロパティまたはメソッド (asp.net mvc の DependecyResolver を考えてください) があります。その場合、Service Locator パターンを使用しています。あなたの例のIWorkはロケーターではなく、単なる依存関係です。

依存関係リゾルバーの例を続けるには、関連するすべての型をコンテナーに登録します。コンテナーはビルドされ、依存関係リゾルバーとして登録されます。次に、asp.net mvc フレームワークは、リゾルバー (Service Locator - SL) を使用して、コントローラー、ビュー、およびこれらに必要なすべての依存関係をインスタンス化します。

フレームワークの一部として SL パターンを使用することは問題ありませんが、アプリでそれを使用してオブジェクトをインスタンス化する場合は、コードがロケーターに結合されるため、問題があります。唯一の解決策である場合もありますが、99% は単なるアンチパターンです。

于 2013-10-08T07:55:30.620 に答える