2013-06-23 130 views
2

enums喜歡在我的數據庫如下:如何用空格表示枚舉值?

「隨機型」,「隨機類型1」,「NewRandom」

通常情況下,我將代表一個枚舉值,如:

enum myTypes 
{ 
    Random Type = 0,... 
} 

,但是這是不可能的,所以我嘗試使用類

static class myTypes 
{ 
    public const string RandomType = "Random Type"; 
    public const string NewRandom = "NewRandom"; 
} 

這樣,我可以使用類如Enum,但我想知道這是否是最好的實現可能?或者在創建Enums以留出空間嗎?

謝謝。

編輯: 請,我也想知道我目前的實施是否有任何問題。我有一種感覺,我現在的實施比這裏提出的大多數解決方案都要好。

由於

+0

尋找T4模板.... –

+0

爲什麼不在調用Enum中的「隨機類型」RandomType? – Magnus

+0

@Magnus:因爲我正在檢索'Enum'名字。 – rtuner

回答

2

枚舉得多類似編號(整數特異性),而不是串左右。堅持編號的枚舉可以讓你輕鬆地投射,標記合成(例如,AND,OR等)。

我不會使用字符串常量來代替枚舉,除非這會爲您帶來更多好處而不是懲罰。

如果您的目標是向用戶描述枚舉選項,我建議考慮使用Description屬性來豐富每個項目。這是一個元數據,而不是真實的數據,但使用反射也很容易閱讀。

乾杯

+0

我正在使用枚舉名稱。 – rtuner

+0

從字符串開始,您應該解析它們以獲取Enum項目。您不能使用Enum對象的「Parse」方法,但可以搜索匹配的描述(for-loop或hash-map)。如果你有很少的選擇,那麼簡單的轉換就足夠了,這是不值得的。 –

0

你應該使用字符串作爲數據庫類型的指標。改用整數。如果你喜歡,你可以在你的數據庫中有一個「類型表」,在那裏你可以存儲類型名,而不是通過使用它們的表重複它們。

如果您這樣做,那麼您可以將數據庫中的整數轉換爲枚舉,如上所示。

2

我所做的是定義可以附加到枚舉值的自定義屬性[DisplayName(string)]。你可以定義你希望被命名爲空格/特殊字符值與顯示名稱的枚舉:

public enum Test 
{ 
    None = 0, 

    [DisplayName("My Value")] 
    MyValue = 1, 

    [DisplayName("Spęćiał")] 
    Special = 2 
} 

你除了獲得枚舉值的名字實施也應該檢查是否DisplayName屬性設置,如果是這樣,它應該改爲顯示名稱。

+0

向我解釋這與'[DescriptionAttribute]'的優點? –

+0

@newStackExchangeInstance您可以控制實現,以便可以根據需要擴展具有更多功能的屬性(例如本地化支持)。 – ghord

+0

我知道你可以做到這一點,但對於這種特殊情況'DescriptionAttribute'更好。 –

1

我會去的顯示名稱屬性:

[AttributeUsage(AttributeTargets.Field)] 
public class EnumDisplayNameAttribute : DisplayNameAttribute 
{ 
    public EnumDisplayNameAttribute() 
     : base(string.Empty) 
    { 
    } 

    public EnumDisplayNameAttribute(string displayName) 
     : base(displayName) 
    { 
    } 
} 


public static class EnumExtensions 
{ 
    public static string ToDisplayName(this Enum enumValue) 
    { 
     var builder = new StringBuilder(); 

     var fields = GetEnumFields(enumValue); 

     if (fields[0] != null) 
      for (int i = 0; i < fields.Length; i++) 
      { 
       var value = fields[i] 
        .GetCustomAttributes(typeof(EnumDisplayNameAttribute), false) 
        .OfType<EnumDisplayNameAttribute>() 
        .FirstOrDefault(); 

       builder.Append(value != null 
            ? value.DisplayName 
            : enumValue.ToString()); 

       if (i != fields.Length - 1) 
        builder.Append(", "); 
      } 

     return builder.ToString(); 
    } 

    private static FieldInfo[] GetEnumFields(Enum enumValue) 
    { 
     var type = enumValue.GetType(); 

     return enumValue 
      .ToString() 
      .Split(new[] { ',', ' ' }, StringSplitOptions.RemoveEmptyEntries) 
      .Select(type.GetField) 
      .ToArray(); 
    } 
} 

使用率類型:

public enum MyType 
{ 
    [DisplayName("Random Type")] 
    RandomType, 
    [DisplayName("New Random")] 
    NewRandom 
} 

是:

var enumVariable = MyType.RandomType; 
var stringRepresentation = enumVariable.ToDisplayName(); 

注意,這種做法你會得到的ToString值如果您省略某些枚舉成員的屬性。

3

不,你不能那樣做。枚舉只是類型安全int s。

有一個解決方案可用,我非常喜歡它。使用DescriptionAttribute

你會使用這樣的:

static enum myTypes 
{ 
    [Description("Random Type")] 
    RandomType, 
    [Descripton("New Random")] 
    NewRandom 
} 

,然後你想也需要這種擴展方法:

public static string GetDescription<T>(this T en) where T : struct, IConvertible 
{ 
    Type type = typeof(T); 
    if (!type.IsEnum) 
    { 
     throw new ArgumentException("The type is not an enum"); 
    } 
    MemberInfo[] memInfo = type.GetMember(en.ToString()); 
    if (memInfo != null && memInfo.Length > 0) 
    { 
     object[] attrs = memInfo[0].GetCustomAttributes(typeof(DescriptionAttribute), false); 
     if (attrs != null && attrs.Length > 0) 
     { 
      return ((DescriptionAttribute)attrs[0]).Description; 
     } 
    } 
    return en.ToString(); 
} 

然後用,你可能只是這樣做:

myTypes.RandomType.GetDescription(); 
0

您可以使用Typesafe Enum模式來實現您的目標。

想法是圍繞一個類包裝你的枚舉。我想這是你想要的 -

public class MyTypes 
{ 
    #region Enum Values 

    public static MyTypes RandomType = new MyTypes(0, "Random Type"); 
    public static MyTypes NewRandom = new MyTypes(1, "New Random"); 

    #endregion 

    #region Private members 

    private int id; 
    private string value; 
    private MyTypes(int id, string value) 
    { 
     this.id = id; 
     this.value = value; 
    } 

    #endregion 

    #region Overriden members 

    public override string ToString() 
    { 
     return value; 
    } 

    #endregion 

    public static List<MyTypes> GetValues() 
    { 
     return new List<MyTypes>() { MyTypes.RandomType, MyTypes.NewRandom }; 
    } 
}