我最近了解了DI框架Guice和Ninject,并希望在我的一些新项目中使用它们。

虽然我熟悉一般的依赖项注入(inject)概念,并且知道如何使用这些框架来构造对象图,但是在涉及动态应用程序行为时,我仍难以应用IoC。

考虑以下示例:

  • 当应用程序启动时,将显示主窗口。
  • 当用户单击主面板时,将打开一个上下文菜单。
  • 根据用户的选择,将创建一个新的用户控件,并将其显示在鼠标位置。
  • 如果用户最终决定关闭该应用程序,将显示一个确认框,并且-确认后将关闭主窗口。

  • 虽然很容易将主窗口的View连接到Presenter/ViewModel,然后将其绑定(bind)到域逻辑,但是我不明白如何干净地(就IoC而言)完成以下任务:
  • 动态实例化一个具体的UI控件(例如IGreenBoxViewIRedImageView JConcreteGreenBoxView,JConcreteRedImageView),而无需使用任何类型的服务定位器模式(例如,再次向IoC请求)
  • 以此为基础,创建一个新模型,演示者并查看实例
  • 类似地,实例化一个新的具体对话框,例如运行时的JOptionPane

  • 我已经看到了使用抽象工厂的一些解决方案,但老实说并没有完全理解它们。看来,这种解决方案将导致某些( View 域,演示者域,...)内部类型暴露给构造根,进而暴露给整个世界。

    所以-我该怎么做呢?

    最佳答案

    如果可以重用控件,则可以在使用控件的地方进行构造函数注入(inject)。否则,您必须注入(inject)工厂:

    public interface IControlFactory
    {
         IGreenBoxView CreateGreenBoxView();
         IRedImageView CreateRedImageView();
    }
    

    并将其注入(inject)您需要创建此控件的位置。

    实现转到容器配置。在那里,您可以将容器注入(inject)到实现中。一些容器提供了自动实现该工厂的功能。例如,在Ninject中:
    Bind<IControlFactory>().ToFactory();
    

    参见https://github.com/ninject/ninject.extensions.factory/wiki

    关于c# - IoC/DI容器,工厂和运行时类型创建,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/9627303/

    10-11 19:30
    查看更多