2009-07-20 21 views
0

我有一個CustomersModule.cs有以下初始化()方法:有人能解釋在Prism的解決<>方法中發生的魔法嗎?

public void Initialize() 
{ 
    container.RegisterType<ICustomersRepository, CustomersRepository>(new ContainerControlledLifetimeManager()); 
    CustomersPresenter customersPresenter = this.container.Resolve<CustomersPresenter>(); 

} 

I類從容器解決看起來是這樣的:

class CustomersPresenter 
{ 
    private CustomersView view; 
    private ICustomersRepository customersRespository; 

    public CustomersPresenter(CustomersView view, 
     ICustomersRepository customersRepository, 
     TestWhatever testWhatever) 
    { 
     this.view = view; 
     this.customersRespository = customersRepository; 
    } 
} 

TestWhatever類只是一個虛擬類我創建:

public class TestWhatever 
{ 
    public string Title { get; set; } 

    public TestWhatever() 
    { 
     Title = "this is the title"; 
    } 

} 

然而,容器高高興興地解決CustomersPresenter即使我從來沒有註冊它,也是集裝箱莫名其妙地發現 TestWhatever,其實例化,並將其注入到CustomersPresenter

我很驚訝地意識到這個,因爲我無法在Prism文檔中找到明確指出容器是如此自動的任何地方。

所以這很好,但容器做的事情我不知道,還有什麼可以做,我不知道? 例如,我可以從其他模塊注入類,如果模塊恰好被加載,容器將注入它們,如果不是,它會注入一個null?

回答

3

沒有什麼不可思議的事情發生。你正在指定具體的類型,所以自然可以解析,因爲如果我們有對象,我們可以調用它的構造函數。

class Fred { }; 

Fred f1 = new Fred(); 

Type t = typeof(Fred); 

Fred f2 = (Fred)t.GetConstructor(Type.EmptyTypes).Invoke(null); 

上面的最後一行是有效的會發生什麼,已經通過你給Resolve類型參數使用typeof發現t類。

如果類型不能由新構造(因爲它在某個未知的獨立代碼庫中),那麼您將無法將其作爲Resolve的類型參數。

在第二種情況下,它是構造函數注入,但它仍然是一個已知的具體可構造類型。通過反射,Unity框架可以爲構造函數獲取所有類型的參數。類型TestWhatever是可修復的,因此對於構建的內容不存在歧義或困難。

至於你對單獨模塊(程序集)的關注,如果你將TestWhatever移動到另一個程序集,那不會改變你寫的代碼行;它只是意味着你必須添加一個對其他程序集的引用來獲得這個程序集。然後TestWhatever仍然是一個明確可重構的可構造類型,所以它可以由Unity構建。換句話說,如果你可以引用代碼中的類型,你可以得到一個Type對象,所以在運行時它可以直接構造。

迴應評論:

如果刪除類TestWhatever,你會得到一個編譯時錯誤,因爲你指的是輸入你的代碼。所以通過這樣做不可能獲得運行時。

在此安排中,解耦仍然有效,因爲您可以註冊TestWhatever的特定實例,因此每次調用Resolve<TestWhatever>()都會得到相同的實例,而不是構建一個新實例。

+0

但是那麼解耦是在哪裏進行的,即如果我需要來自另一個模塊的類「MenuManager」,並且該模塊沒有碰巧被加載,我就理解容器應該例如注入null以便應用程序可以在有或沒有其他部分的情況下運行,但是如果我刪除類「TestWhatever」的應用程序會得到一個錯誤。 – 2009-07-20 14:06:33

2

這個工作的原因是因爲Unity是爲它設計的。當您使用具體類型進行解析時,Unity會查看它是否可以從容器中解析出來。如果它不能,那麼它就會去實例化解析它的依賴類型。這真的很簡單。

相關問題