在实际开发中,在数据库表设计中,我们往往习惯于用一个Int类型的State字段去表示数据的状态,这个字段很方便去表示这条数据的状态,但是又不愿意去建一张这个State字段的外键表去解释状态。
我们一般会把这个State字段当成一个约定,去在项目中应用(比如:0:启用,1:禁用)
在后台管理或其它地方显示Int类型对应的实际状态时,再到公共类中去写一个方法,里面用一个switch...case去返回对应的中文解释。
但是我习惯于用一个Enum枚举去规范数据库去所有的State字段,Enum的使用,也更利于开发,可以分别对枚举注释,约定可以呈现在开发人员眼前,而不是直接凭空约定。下面分享一下我对Enum类的使用。
1.首先,我们可以对枚举类型建立一个实体类:ReadEnum
view plainprint?
public class ReadEnum
{
public string Name { get; set; }
public int Value { get; set; }
}
2.第二步,创建State字段对应的枚举
view plainprint?
#region##状态枚举(数据库里所有State枚举)
/// <summary>
/// 状态枚举(数据库里所有State枚举)
/// 创建人:Porschev
/// 创建时间:2011-7-19
/// </summary>
public enum ssnState
{
/// <summary>
/// 启用
/// </summary>
<span style="color:#ff0000;">[Description("启用")]</span>
Enabled = 0,
/// <summary>
/// 禁用
/// </summary>
<span style="color:#ff0000;">[Description("禁用")]</span>
Disable = 1
}
#endregion
如上面创建的枚举,开发者在使用枚举时一般都不会用到红色部分Description属性,它在System.ComponentModel命名空间下
有了它,我们完全可以不用以前使用的switch...case方法去释义或显示中文。
第三步:对所有Enum写一些应用方法
view plainprint?
#region##获得Enum类型description
/// <summary>
/// 获得Enum类型description
/// 创建人:Porschev
/// 创建时间:2011-7-19
/// </summary>
/// <param name="enumType">枚举的类型</param>
/// <param name="val">枚举值</param>
/// <returns>string</returns>
public static string GetEnumDesc(Type enumType, object val)
{
string enumvalue = System.Enum.GetName(enumType, val);
if (string.IsNullOrEmpty(enumvalue))
{
return "";
}
System.Reflection.FieldInfo finfo = enumType.GetField(enumvalue);
object[] enumAttr = finfo.GetCustomAttributes(typeof(System.ComponentModel.DescriptionAttribute), true);
if (enumAttr.Length > 0)
{
System.ComponentModel.DescriptionAttribute desc = enumAttr[0] as System.ComponentModel.DescriptionAttribute;
if (desc != null)
{
return desc.Description;
}
}
return enumvalue;
}
#endregion
#region##获取某个枚举的全部信息
/// <summary>
/// 获取某个枚举的全部信息
/// 创建人:Porschev
/// 创建时间:2011-7-19
/// </summary>
/// <typeparam name="T">枚举</typeparam>
/// <returns>枚举的全部信息</returns>
public static List<ReadEnum> GetEnumList<T>()
{
List<ReadEnum> list = new List<ReadEnum>();
ReadEnum re = null;
Type type = typeof(T);
foreach (int enu in System.Enum.GetValues(typeof(T)))
{
re = new ReadEnum();
re.Name = GetEnumDesc(type, enu);
re.Value = enu;
list.Add(re);
}
return list;
}
#endregion
#region##根据值返回枚举对应的内容
/// <summary>
/// 根据值返回枚举对应的内容
/// 创建人:Porschev
/// 创建时间:2011-7-19
/// </summary>
/// <typeparam name="T">枚举</typeparam>
/// <param name="value">值(int)</param>
/// <returns></returns>
public static T GetModel<T>(int value)
{
T myEnum = (T)System.Enum.Parse(typeof(T), value.ToString(), true);
return myEnum;
}
#endregion
#region##根据值返回枚举对应的内容
/// <summary>
/// 根据值返回枚举对应的内容
/// 创建人:Porschev
/// 创建时间:2011-7-19
/// </summary>
/// <typeparam name="T">枚举</typeparam>
/// <param name="value">值(string)</param>
/// <returns></returns>
public static T GetModel<T>(string value)
{
T myEnum = (T)System.Enum.Parse(typeof(T), value, true);
return myEnum;
}
#endregion
这几个方法完全可以满足在项目中对Enum枚举的使用。
第四步:测式方法
view plainprint?
string str = GetEnumDesc(typeof(ssnState), 0);
//结果:启用
List<ReadEnum> list = GetEnumList<ssnState>();
//结果:list.Count=2
// 第一个元素:Name:启用;Value:0
// 第二个元素:Name:禁用;Value:1
ssnState re = GetModel<ssnState>(0);
//结果:ssnState.Enabled
ssnState re1 = GetModel<ssnState>("0");
//结果:ssnState.Enabled
<combobox>.BindEnumKeyValue(typeof(<enum>));
or
<combobox>.BindEnumDescriptionValue(typeof(<enum>));
public static class ComboBoxEx
{
public static void BindEnumKeyValue(this ComboBox obj, Type enumType)
{
obj.DataSource = enumType.EnumToList();
obj.DisplayMember = "Key";
obj.ValueMember = "Value";
}
public static void BindEnumDescriptionValue(this ComboBox obj, Type enumType)
{
obj.DataSource = enumType.EnumDescriptionToList();
obj.DisplayMember = "Key";
obj.ValueMember = "Value";
}
}
public static class EnumEx
{
public static IList EnumToList(this Type enumType)
{
List<KeyValuePair<string, int>> list = new List<KeyValuePair<string, int>>();
foreach (Enum key in Enum.GetValues(enumType))
{
int value = (int)Enum.Parse(enumType, key.ToString());
list.AddUnique(new KeyValuePair<string, int>(key.ToString(), value));
}
return list.SortByKey();
}
public static IList EnumDescriptionToList(this Type enumType)
{
List<KeyValuePair<string, int>> list = new List<KeyValuePair<string, int>>();
foreach (Enum key in Enum.GetValues(enumType))
{
int value = (int)Enum.Parse(enumType, key.ToString());
list.AddUnique(new KeyValuePair<string, int>(key.GetEnumDescription(), value));
}
return list.SortByKey();
}
public static string GetEnumDescription(this Enum value)
{
return GetEnumAttribute(value, typeof(DescriptionAttribute));
}
public static string GetEnumCategory(this Enum value)
{
return GetEnumAttribute(value, typeof(CategoryAttribute));
}
public static string GetEnumAttribute(this Enum value, Type attribute)
{
Type type = value.GetType();
if (value == null)
{
throw new ArgumentException("Value must be of type Enum", "Value");
}
System.Reflection.MemberInfo[] memberInfo = type.GetMember(value.ToString());
if (memberInfo != null && memberInfo.Length > 0)
{
object[] attrs = memberInfo[0].GetCustomAttributes(attribute, false);
if (attrs != null && attrs.Length > 0)
{
return ((DescriptionAttribute)attrs[0]).Description;
}
}
return value.ToString();
}
}
public static class ListKeyValuePairEx
{
public static List<KeyValuePair<K, V>> AddUnique<K, V>(this List<KeyValuePair<K, V>> list, KeyValuePair<K, V> kv)
{
if (!list.Contains(kv))
list.Add(kv);
return list;
}
public static List<KeyValuePair<K, V>> SortByKey<K, V>(this List<KeyValuePair<K, V>> list)
{
List<KeyValuePair<K, V>> sorted = new List<KeyValuePair<K, V>>();
foreach (KeyValuePair<K, V> item in list.OrderBy(key => key.Key))
{
sorted.Add(new KeyValuePair<K, V>(item.Key, item.Value));
}
return sorted;
}
public static List<KeyValuePair<K, V>> SortByValue<K, V>(this List<KeyValuePair<K, V>> list)
{
List<KeyValuePair<K, V>> sorted = new List<KeyValuePair<K, V>>();
foreach (KeyValuePair<K, V> item in list.OrderBy(key => key.Value))
{
sorted.Add(new KeyValuePair<K, V>(item.Key, item.Value));
}
return sorted;
}
}