簡體   English   中英

枚舉到字典

[英]Enum to dictionary

我想實現一個將枚舉轉換為字典的擴展方法:

public static Dictionary<int, string> ToDictionary(this Enum @enum)
{
    Type type1 = @enum.GetType();
    return Enum.GetValues(type1).Cast<type1>()
        //.OfType<typeof(@enum)>()
        .ToDictionary(e => Enum.GetName(@enum.GetType(), e));
}

為什么不編譯?

一個錯誤:

“找不到類型或命名空間名稱‘type1’(您是否缺少 using 指令或程序集引用?)”

喬恩斯基特寫了你需要的一切;)

但是這里你的代碼正在運行:

public static Dictionary<int, string> ToDictionary(this Enum @enum)
{
  var type = @enum.GetType();
  return Enum.GetValues(type).Cast<int>().ToDictionary(e => e, e => Enum.GetName(type, e));
}

好吧,您正在嘗試使用Type變量作為泛型類型參數。 你不能用泛型來做到這一點,泛型是關於編譯時類型的。

您可以使用反射來實現,但最好將其設為通用方法。 不幸的是,您不能將泛型類型參數限制為枚舉,盡管我在Unconstrained Melody 中有一些技巧可以解決這個問題。

如果做不到這一點,您可以只對泛型方法使用struct類型約束,這將是一個好的開始。

現在,下一個問題是您正在嘗試獲取Dictionary<int, string> - 但枚舉的值不是int值。 它們可能可以轉換int值,但它們不會立即存在。 你可以使用Convert.ToInt32來做到這一點,但你必須做一些事情

最后(目前)您希望使用uintlong底層類型的枚舉發生什么?

您不能將 type1 用作泛型參數,因為它是一個變量,而不是一個類型。

以下代碼您的代碼顯示的內容類似

public static Dictionary<string, TEnum> ToDictionary<TEnum>()
    where TEnum : struct
{
    if (!typeof(TEnum).IsEnum)
        throw new ArgumentException("Type must be an enumeration");
    return Enum.GetValues(typeof(TEnum)).Cast<TEnum>().
            ToDictionary(e => Enum.GetName(typeof(TEnum), e));
}

像這樣使用它:

ToDictionary<Colors>()

但我不太確定,這是,你所期望的嗎?

此外,它還有一個問題:您可以傳遞任何結構,而不僅僅是枚舉,這將導致運行時異常。 有關更多詳細信息,請參閱Jon 的回答

基於丹尼爾的解決方案

public static SelectList ToSelectList<TEnum>(this HtmlHelper h) where TEnum : struct
{
    return new SelectList(FortunaExtension.ToDictionary<TEnum>(), "Key", "Value");
}

這是我用來轉換枚舉的擴展方法。 唯一的區別是我為了我的目的返回 IEnumerbale<KeyValuePair<int, int>> :

public static IEnumerable<KeyValuePair<int, string>> ToListOfKeyValuePairs<TEnum>(this TEnum enumeration) where TEnum : struct
{
    return from TEnum e in Enum.GetValues(typeof(TEnum))
            select new KeyValuePair<int, string>
                (
                    (int)Enum.Parse(typeof(TEnum), e.ToString()),
                    Regex.Replace(e.ToString(), "[A-Z]", x => string.Concat(" ", x.Value[0])).Trim()
                );
}

它還為值添加了空格。

例子:

enum Province
{
    BritishColumbia = 0,
    Ontario = 1
}

用法:

<select>
<% foreach(var item in Province.BritishColumbia.ToListOfKeyValuePairs()){ %>
    <option value="<%=item.Key %>"><%=item.Value %></option>
<% } %>
</select>

輸出:

<select>
    <option value="0">British Columbia</option>
    <option value="1">Ontario</option>
</select>

雖然@Paul Ruane 是正確的,但我發現這是一個非常有用的擴展方法。 這不是一個完美的世界。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM