2011-12-27 57 views
0

在我的程序中,我使用枚舉來表示對象的當前狀態。我希望能夠一一瀏覽這個枚舉的值。枚舉值在數值上是連續的並且以0開始的事實是給定的。多個程序集中的動態類型轉換行爲

雖然試圖編寫一個遞增枚舉的函數,但如果它已達到最終結果,則會產生問題。

public static TEnum IncrWrap<TEnum>(TEnum value) 
{ 
    int len = Enum.GetNames(typeof(TEnum)).Length; 
    dynamic wrapper = value; 
    dynamic newValue = ((int)wrapper + 1) % len; 
    return (TEnum)newValue; 
} 

如果IncrWrap方法中相同的組件(項目),其調用它的對象存在,它完美。但是,如果我將它移動到另一個項目(更高級別以便更多的東西可以使用它)並從dll中調用它,那麼當它試圖將wrapper轉換爲int並顯示消息「無法轉換類型」時,我會得到RuntimeBinderException System.Enum'改爲'int'「。

怎麼了?我不明白爲什麼從不同的程序集中調用函數會導致函數的行爲如此不同。有什麼關於dynamic我不明白?這將是很好的,不必使用反射來做到這一點。

回答

1

不幸的是枚舉在這裏構成了一些問題。首先枚舉可以有任何整型,除char之外。其次,不能保證枚舉具有遞增的基礎類型值。最後,C#語言不支持通用類型約束System.Enum,這會有所幫助。說了這麼多,我相信你能有點不同解決您的問題:

public static TEnum NextEnum<TEnum>(TEnum value) 
{ 
    if (!typeof(TEnum).IsEnum) 
     throw new ArgumentException("Expected type of System.Enum", "value"); 

    var values = Enum.GetValues(typeof (TEnum)); 
    var index = Array.IndexOf(values, value); 
    return (TEnum)Enum.ToObject(typeof (TEnum), values.GetValue((index + 1) % values.Length)); 
} 

實際上,我驚訝,你都能夠找到,使用您的動態解決方案正常工作。

+0

還有一個問題:如果'value'的值不是枚舉的定義值之一,Array.IndexOf可能會返回-1。 – phoog 2011-12-28 00:20:04

+0

太棒了!謝謝。仍然好奇爲什麼我的方法在兩種情況下表現不同,但這種解決方案絕對更好。 – Lucina 2011-12-28 01:34:53