[〜#〜] solid [〜#〜] の原則の5番目の概念は 依存関係の逆転の原則 です。 依存性注入 と 制御の反転 に大きく関連しており、これらの概念のいずれかに言及する場合、それらは互いに同義となるように使用されることが多い。例:
Autofacは、.NET Core、ASP.NET Core、.NET 4.5.1+、ユニバーサルWindowsアプリなどの中毒性のあるInversion of Controlコンテナーです。
そして
制御の反転(IoC)原則のSpring Framework実装。 IoCは、依存性注入(DI)とも呼ばれます。
ここでは、自動ファクトリーを、構成に基づいてオブジェクトを構築するファクトリーとして定義しています。 AutofacとSpringは2つの例です。技術的にはIoCコンテナとして設計されていますが、広く言えば自動ファクトリとして使用されます。
Autofac または Spring IoC "Dependency Injection"フレームワークを呼び出す人がよくいます。 例 :
これをIoC(制御の反転)コンテナーまたはDI(依存性注入)フレームワークと呼ぶことができます。
オンラインドキュメントの多くは、自動工場の手荷物を持っているようです。一見すると、SOLIDの原則は、オブジェクトを構築するための自動ファクトリーを正式には必要としないようです。しかし、これは、依存関係の反転の結果、 SOLID principal?を正しく実装するにはファクトリが必要ですアプリの最高レベルが依存関係を構築し、最高レベルのクラスのコンストラクターにそれらを入れます、これはSOLID principleに従っていますか?または、はIoCコンテナーですこれに必要ですか?
このC#の例を見てください
public interface IMessageSender
{
void SendMessage(string message);
}
public class ConsoleMessageSender : IMessageSender
{
public void SendMessage(string message)
{
Console.WriteLine(message);
}
}
public interface IApp
{
void SendHelloMessage();
}
public class App : IApp
{
private IMessageSender _messageSender;
public App(IMessageSender messageSender)
{
_messageSender = messageSender;
}
public void SendHelloMessage()
{
_messageSender.SendMessage("Hello World!");
}
}
これがバージョンA)で、IoC /自動ファクトリーがありません。
class Program
{
static void Main(string[] args)
{
var app = new App(new ConsoleMessageSender());
app.SendHelloMessage();
}
}
これはバージョンB)で、IoCコンテナ用にAutofacを使用しています
class Program
{
static void Main(string[] args)
{
var builder = new ContainerBuilder();
builder.RegisterType<ConsoleMessageSender>().As<IMessageSender>();
builder.RegisterType<App>().As<IApp>();
var container = builder.Build(ContainerBuildOptions.None);
var app = container.Resolve<IApp>();
app.SendHelloMessage();
}
}
バージョンB)はより正確ですSOLID観点から?バージョンA)はSOLIDに準拠しませんか? IoCコンテナがないための原則ですか?
注:ここで明確な定義を探しています。 IoCコンテナーは、DIおよびSOLIDの概念にバンドルされることがよくありますが、問題は、それらが厳密に必要かどうかです。 SOLIDに追加された装身具であるかどうかという疑問があります
SOLID原理を正しく実装するために自動ファクトリーが必要なのは、依存関係の逆転の結果ですか?
番号。
IoCコンテナは、オブジェクトをインスタンス化する便利な方法にすぎません。彼らはSOLIDの義務ではありません。コンテナなしで同じオブジェクトをインスタンス化でき、それでもSOLIDであることができます。
アプリの最高レベルが依存関係を構築し、それを最高レベルのクラスのコンストラクターに渡す場合、これはSOLID原則に従っていますか?
基本的にそうです。
集合ルート(コンソールアプリケーションの場合、main
メソッドの場合もあります)は、プログラムを作成するオブジェクトグラフを立ち上げる責任があります(または集約)作業。
バージョンB)はSOLIDの観点から)より正しいですか?
番号。
SOLIDの原則は、コンテナではなくクラスおよびクラス階層に基づいています。コンテナはオブジェクトグラフを立てる1つの方法ですが、それだけがコンテナではありません。 SOLIDはコンテナに依存しません。
IoCコンテナーがないため、バージョンA)はSOLIDの原則に準拠できませんか?
番号。
DependencyInjectionとDependencyInversionの混乱にあなたの痛みを感じます。私は多くの就職の面接を受けており、違いを説明する必要があります。
IoCコンテナーが必要であるとは言えませんが、大きな依存関係ツリーのインスタンス化がはるかに簡単になります。ただし、コードがSOLI [〜#〜] d [〜#〜]の後に続く場合、IoCコンテナを使用するかどうかは関係ありません。理想的なコードベースでは、コードは、コードが存在するIoCコンテナーについての知識を持っていてはなりません。
依存関係Inversionは、他のクラスを必要とする他のクラスを必要とする多くのクラスにつながることが多く、一部のクラスは他の多くのクラスによって使用され、多くの場合、有効期間が異なります。クラスが2つしかないため、この例ではこの問題を正義に実行できません。代わりに、数百のクラス、さらに多くのインターフェース(クラスは複数のインターフェースを公開できるため)、およびそれらの間の依存関係の複雑な非循環グラフの例を想像してください。この種の例では、手動のインスタンス化コードは、IoCの登録と解決の組み合わせだけよりもはるかに複雑で混乱します。