如何使用Ninject实现松散耦合

时间:2013-01-11 08:47:47

标签: c# ninject loose-coupling

我是Ninject的新手。有人可以帮我实现我想要的。 我会举个例子。请帮助我如何使用NInject来松耦合。

假设我在下面给出了一个界面。

public interface IVehicle
{
 PrintSpecification();
}

现在我有三个类实现上面的接口。它们可以如图所示。

public class Car implements IVehicle
{      
 public void PrintSpecification()
 { Console.WriteLine("Specification for Car");}
}

public class Bus implements IVehicle
{
  public void PrintSpecification()
  { Console.WriteLine("Specification for Bus");}
}

public class Truck implements IVehicle
{
  public void PrintSpecification()
  { Console.WriteLine("Specification for Truck");}
}

现在在我的主程序中,我会有类似的东西。在这里,我使用new运算符创建了CarBusTruck的三个具体实现。我必须显示所有三种车辆的规格。现在我想知道如何编写Ninject代码,以便不依赖于具体的类。

Public static void main()
{
  IVehicle v1=new Car();
  IVehicle v2=new Bus();
  IVehicle v3=new Truck();
  v1.PrintSpecification();
  v2.PrintSpecification();
  v3.PrintSpecification();
}

2 个答案:

答案 0 :(得分:2)

您可以通过以下方式绑定所有规范:

public class AutoModule : NinjectModule
{
    public override void Load()
    {
        Bind<IVehicle>().To<Car>();
        Bind<IVehicle>().To<Bus>();
        Bind<IVehicle>().To<Truck>();
    }
}

并在您的应用中:

IKernel kernel = new StandardKernel(new AutoModule());

kernel.Bind<Inspector>().ToSelf();

class Inspector
{
      IVehicle[] vehicles;
      public Inspector(IVehicle[] vehicles)
      {
          this.vehicles=vehicles;
      }
      public void PrintSpecifications()
      {
           foreach(var v in vehicles )
           {
              v.PrintSpecification();
            }
      }
}

//automatic injection in constructor
kernel.Get<Inspector>().PrintSpecifications();

如果您想要某种方式有条件地绑定一个实现,您可以使用

  • 命名绑定
  • 条件绑定
  • 上下文绑定

There is a good documentation inthe NInject wiki

如果您需要在模块中映射多个tyes,请考虑使用一些命名约定并创建一些自动绑定策略。

您也应该努力与IoC容器分离,看看Composition Root Pattern的工作原理。

答案 1 :(得分:1)

使用IVehicle实现的命名绑定创建模块:

public class AutoModule : NinjectModule
{
    public override void Load()
    {
        Bind<IVehicle>().To<Car>().Named("Small");
        Bind<IVehicle>().To<Bus>().Named("Big");
        Bind<IVehicle>().To<Truck>().Named("Huge");
    }
}

按名称获取您的车辆:

IKernel kernel = new StandardKernel(new AutoModule());
IVehicle v1 = kernel.Get<IVehicle>("Small");
IVehicle v2 = kernel.Get<IVehicle>("Huge");
IVehicle v3 = kernel.Get<IVehicle>("Big");
v1.PrintSpecification();
v2.PrintSpecification();
v3.PrintSpecification();