2011-02-28 28 views
1

這裏是我的問題: 我正在修改我公司開發的框架,並且我們有一個函數返回類屬性中的任何更改。 這是在框架結構:使用反射的泛型繼承問題

namespace Fwk.Business.Entities 

    public class BusinessEntity : IIdentifiable, ICloneableExt 
    { 
     ... 
    } 

    public class EntityList<BE> where BE : BusinessEntity, new() 
    { 
     ... 
    } 
} 

,這是一個使用tipical:

namespace Common.Business.Entities 
{ 

    public class ImportFileEntity : Fwk.Business.Entities.BusinessEntity 
    { 
     ... 
    } 

    public class ImportFileList : Fwk.Business.Entities.EntityList<ImportFileEntity> 
    { 
    } 

} 

Fwk.Business.Entities.BusinessEntity具有如下功能命名GetChanges(),通過所有使用反射迭代屬性並檢查它們是否改變了它們的值(使用原始BusinessEntity的副本)。它甚至檢查該屬性本身是否是Fwk.Business.Entities.BusinessEntity的一個實例,如果是,則遞歸調用GetChanges方法。但我的問題是,當我有一個屬性是Fwk.Business.Entities.EntityList的一個實例。我想調用每個元素的GetChanges方法,但我似乎無法識別這些EntityList屬性。 我試着

pi.GetValue(this, null).GetType().IsSubclassOf(typeof(EntityList<BusinessEntity>)) 

其中pi是標識我檢查的屬性的PropertyInfo元素,但這返回false。我也嘗試了很多其他的Type函數,比如IsInstanceOfType和IsAssignableFrom,在我需要true的地方總是會出現錯誤。 奇怪的是,如果我檢查特定的BusinessEntity類型,它的工作:

pi.GetValue(this, null).GetType().IsSubclassOf(typeof(EntityList<ImportFileEntity>)) 

,但當然這是不能接受的,因爲我可以有任何的BusinessEntity的列表。

任何人都可以幫我解決這個問題嗎?

比所有的回覆 亞歷克斯。

UPDATE: SLaks給了我一個很好的回答,我這個編碼:做

EntityList<BusinessEntity> elList = (EntityList<BusinessEntity>)pi.GetValue(this, null); 

阿當

bool isEntityList = false; 
Type thisType = (pi.GetValue(this, null) ?? new object()).GetType(); 
while (thisType != typeof(object) && !isEntityList) 
    if (thisType.IsGenericType && thisType.GetGenericTypeDefinition() == typeof(EntityList<>)) 
     isEntityList = true; 
    else 
     thisType = thisType.BaseType; 

// If property is a subclass of EntityList, invoke GetChanges method. 
if (isEntityList) 
{ 
    EntityList<BusinessEntity> elList = (EntityList<BusinessEntity>)pi.GetValue(this, null); 
    foreach (BusinessEntity beEntity in elList) 
     returnValue += beEntity.GetChanges(messageFormat, stopAtFirstDifference); 
} 

但我發現了一個轉換異常!我認爲我的問題是C#3.5不接受協變(對我來說是新東西,而在4.0中是存在的)。所以我不得不暴露與列表中的財產BusinessEntities

在EntityList在哪裏:BusinessEntity的,新的()

public virtual List<BusinessEntity> ItemsAsBE 
{ 
    get 
    { 
     List<BusinessEntity> returnValue = new List<BusinessEntity>(this.Items.Count); 
     foreach (BusinessEntity item in this.Items) 
      returnValue.Add(item); 
     return returnValue; 
    } 
} 

,並在BusinessEntity的

// If property is a subclass of EntityList, invoke GetChanges method. 
if (isEntityList) 
{ 
    foreach (BusinessEntity beEntity in thisType.GetProperty("ItemsAsBE").GetValue(pi.GetValue(this, null), null) as List<BusinessEntity>) 
     returnValue += beEntity.GetChanges(messageFormat, stopAtFirstDifference); 
} 

謝謝大家!希望這有助於未來的人!

+0

而當屬性爲類型的BusinessEntity []是什麼呢? – SWeko 2011-02-28 15:12:34

+0

不需要擔心,因爲我們「訓練有素」使用相應的「List」類。儘管感謝您的領導。 – Alex 2011-02-28 16:52:49

回答

3

您需要通過Type的基本類型遞歸循環,並尋找一個類型的IsGenericType和其GetGenericTypeDefinition() == typeof(EntityList<>)

+0

非常感謝,SLaks,這個工作!但我現在遇到了另一個問題...請參閱上面的我的編輯 – Alex 2011-02-28 16:19:32