2011-06-23 18 views
0

我已經定義像這樣一個工廠:如何動態地將類型傳遞給一個通用工廠?

public IPopulator CreatePopulator<T>(ReportItem Item) where T : IReportElement 
    { 
     if (typeof(T) == typeof(BarChartElement)) 
     { 
      return BarChartPopulator.Create(Item); 
     } 
     else 
     { 
      throw new NotSupportedException(string.Format("Type: {0} is not suppported by {1}", typeof(T).Name, this.GetType().Name)); 
     } 
    } 

在調用此方法我有一個這樣的變量的類:如何

IReportElement MyElement { get; set; } 

假設MyElement被實例化,以實現IReportElement一個類型,我可以使用這個變量調用我的工廠嗎?

我已經試過

Type VariableType = MyChartElement.GetType(); 
PopulatorFactory.CreatePopulator<VariableType>(new Chart()); 

而且

PopulatorFactory.CreatePopulator<MyVariable.GetType()>(new Chart()); 

我可以寫一個switch語句,但我覺得應該有一些辦法,我通過我的類型。這可能嗎 ?

+0

這是可能的反思。這是你的情況的一個選項? –

+0

反射是一個選項。 – BentOnCoding

+1

我認爲這是[如何使用反射調用通用方法]的副本(http://stackoverflow.com/questions/232535/how-to-use-reflection-to-call-generic-method)。 –

回答

3

你不能像這樣使用變量作爲泛型參數。他們可以提供類型安全的唯一方法是如果類型在編譯時間已知。

您所描述的工廠方法往往被實現爲switch語句,並且沒有什麼內在錯誤。您可以將枚舉類型傳遞給您的工廠方法,該方法將返回實現IReportElement的類型的實例。

無論如何,我並不完全明白你要完成的事情。您的通用工廠方法正在檢查參數的類型。如果你必須檢查這個類型,那麼它就不再是通用的了,那麼有什麼意義呢?

也許你可以深入探討一下你實際上試圖用這段代碼解決什麼問題。可能有更好的選擇,你還沒有考慮。

+0

我簡化了代碼的例子目的..這不是工廠的實際實施,因爲它更大。切換語句與if語句是不重要的實現細節。你會如何使用反射來獲取變量的類型? – BentOnCoding

+0

我會說這應該是最後的手段。如果能夠以更簡單,更安全,更高效的方式實現,則應該是比它應該的更好。 –

+0

它並不重要。當我重構時,我把DRY原則推到了極限。 – BentOnCoding

2

如果你正在使用一個無法改變的圖書館,就像科比建議的那樣,應該這樣的工作。

typeof (PopulatorFactory) 
    .GetMethod("CreatePopulator") 
    .GetGenericMethodDefinition() 
    .MakeGenericMethod(new[] {myVariable.GetType()}) 
    .Invoke(null, new object []{new Chart()}); 
相關問題