2013-11-15 160 views
0

讓我們在C#中說我已經被稱爲A類依賴屬性和構造函數的參數使用Unity

public class A : IInterfaceA 
{ 

[Dependency] 
B _b; 


} 

然後在B級我有這樣一個構造函數:

public class B 
{ 

... 

public B(string someParam) { ... } 

... 

} 

現在,我註冊類一個這樣的:

_unityContainer.RegisterType<IInterfaceA, A>("RegistrationA"); 

,並解決我做的接口:

_unityContainer.Resolve<IInterfaceA>("RegistrationA", new ParameterOverride("someParam", "The param.")); 

現在我想知道是否是解決類和傳遞這樣的參數是好的做法,或者我應該以另一種方式做。 非常感謝:)

回答

0

首先,您發佈的代碼不起作用:實際上,您將重寫類A的參數,而在您的代碼中,參數的構造函數爲B

一般來說,使用參數覆蓋是不是在我看來,一個好的做法(除非一些非常特異性目的情況下像一個控制檯應用程序或使用現有容器的Web服務,但它在大多數情況下可避免),這些原因:

  1. 使用Resolve看起來像一個服務定位器:現今的反模式。你會發現很多關於搜索的討論。
  2. 使用ParameterOverride意味着客戶端(Resolve的調用者)完全知道映射到容器中的類型,並希望使用特定參數初始化該類型。但這與控制反轉相反。

最好的方法是使用抽象工廠。您可以在代碼中添加和使用更加靈活和固體抽象工廠:

public interface BFactory { 

    B Create(string bparam); 

} 

public class BFactoryUnity : BFactory { 
    private IUnityContainer container; 

    public BFactoryUnity(IUnityContainer container) { 
    this.container = container; 
    } 

    public B Create(String bParam) { 
     var b = new B(bParam); 
     container.BuildUp(b); 
     return b; 
    } 
} 

所以,你可以註冊:

_unityContainer.RegisterType<IInterfaceA, A>("RegistrationA") 
      .RegisterType<BFactory, BFactoryUnity>(); 

現在,客戶端可以解決只有工廠,並使用它:

var bFactory = _container.Resolve<BFactory>(); 
var b = bFactory.Create(); 

現在,在一個大的應用程序中,你將需要很多類似的工廠。爲了避免抽象工廠和實現的樣板代碼,您可以在Web中找到自動抽象工廠擴展的一些實現。

+0

你好你好,謝謝你的回答! 我可以使用Unity自動工廠來實現您所寫的內容嗎? 我的意思是這樣的: '容器。RegisterType ( 新InjectionFactory(C => 新函數功能(bParam =>新B(bparam))) );' 然後 '類BFactory { 私人Func鍵工廠; public BFactory(Func factory) { this.factory = factory; } public B Create(string bParam) { return factory(bParam); }' 然後註冊工廠並注入autofactory。 我不確定它是否可以編譯,因爲我現在無法測試它,但這就是我的想法。非常感謝 ! –

+0

是的,這是一個選項。 – onof

相關問題