[C#].NET/C#程序开发获取枚举属性的方法有哪些呢?

C#开发 作者: Rector 283阅读 0评论 0收藏 收藏本文

郑重申明:本文未经许可,禁止任何形式转载

.NET&&C#程序开发

问题描述

在.NET/C#程序开发中,是否有方法获取枚举中的描述信息,而不是枚举的名称或者值本身呢?比如我们有如下的枚举:

using System.ComponentModel; // DescriptionAttribute所在的命名空间

enum FunkyAttributesEnum
{
    [Description("枚举的描述1")]
    NameWithoutSpaces1,
    [Description("枚举的描述2")]
    NameWithoutSpaces2
}

以上枚举,我们获取枚举的值是比较容易的,如:

Array values = System.Enum.GetValues(typeof(FunkyAttributesEnum));
foreach (int value in values)
    Tuple.Value = Enum.GetName(typeof(FunkyAttributesEnum), value);

但是,现在的需求是需要通过一个枚举值,获取到枚举的对应描述信息,在.NET/C#程序开发中,我们应该如何来实现呢?

方案一

以下几个方法可以获取枚举的属性信息,如:

var type = typeof(FunkyAttributesEnum);
var memInfo = type.GetMember(FunkyAttributesEnum.NameWithoutSpaces1.ToString());
var attributes = memInfo[0].GetCustomAttributes(typeof(DescriptionAttribute), false);
var description = ((DescriptionAttribute)attributes[0]).Description;

方案二

创建一个静态扩展方法,并且是泛型的静态扩展方法,用以获取我们需要的枚举泛型属性信息,如:

public static class EnumHelper
{
    public static T GetAttributeOfType<T>(this Enum enumVal) where T:System.Attribute
    {
        var type = enumVal.GetType();
        var memInfo = type.GetMember(enumVal.ToString());
        var attributes = memInfo[0].GetCustomAttributes(typeof(T), false);
        return (attributes.Length > 0) ? (T)attributes[0] : null;
    }
}

调用示例:

string desc = myEnumVariable.GetAttributeOfType<DescriptionAttribute>().Description;

方案三

同样是一个泛型的静态扩展方法,此方法使用LINQ来实现,如:

public static Expected GetAttributeValue<T, Expected>(this Enum enumeration, Func<T, Expected> expression)
        where T : Attribute
    {
        T attribute =
          enumeration
            .GetType()
            .GetMember(enumeration.ToString())
            .Where(member => member.MemberType == MemberTypes.Field)
            .FirstOrDefault()
            .GetCustomAttributes(typeof(T), false)
            .Cast<T>()
            .SingleOrDefault();

        if (attribute == null)
            return default(Expected);

        return expression(attribute);
    }

调用示例:

string description = targetLevel.GetAttributeValue<DescriptionAttribute, string>(x => x.Description);

方案四

另外一个关于读取枚举属性信息的静态扩展方法:

using System;
using System.ComponentModel;

public static class EnumExtensions {

    public static T GetAttribute<T>(this Enum value) where T : Attribute {
        var type = value.GetType();
        var memberInfo = type.GetMember(value.ToString());
        var attributes = memberInfo[0].GetCustomAttributes(typeof(T), false);
        return (T)attributes[0];
    }
    public static string ToName(this Enum value) {
        var attribute = value.GetAttribute<DescriptionAttribute>();
        return attribute == null ? value.ToString() : attribute.Description;
    }

}

使用示例:

using System.ComponentModel;

public enum Days {
    [Description("Sunday")]
    Sun,
    [Description("Monday")]
    Mon,
    [Description("Tuesday")]
    Tue,
    [Description("Wednesday")]
    Wed,
    [Description("Thursday")]
    Thu,
    [Description("Friday")]
    Fri,
    [Description("Saturday")]
    Sat
}

调用:

Console.WriteLine(Days.Mon.ToName());

或者

var day = Days.Mon;
Console.WriteLine(day.ToName());

方案五

另一个基于LINQ的读取枚举属性信息的静态扩展方法:

public static DisplayAttribute GetDisplayAttributesFrom(this Enum enumValue, Type enumType)
{
    return enumType.GetMember(enumValue.ToString())
                   .First()
                   .GetCustomAttribute<DisplayAttribute>();
}

调用示例:

public enum ModesOfTransport
{
    [Display(Name = "Driving",    Description = "Driving a car")]        Land,
    [Display(Name = "Flying",     Description = "Flying on a plane")]    Air,
    [Display(Name = "Sea cruise", Description = "Cruising on a dinghy")] Sea
}

void Main()
{
    ModesOfTransport TransportMode = ModesOfTransport.Sea;
    DisplayAttribute metadata = TransportMode.GetDisplayAttributesFrom(typeof(ModesOfTransport));
    Console.WriteLine("Name: {0} \nDescription: {1}", metadata.Name, metadata.Description);
}

输出结果:
Name: Sea cruise
Description: Cruising on a dinghy

阅读了该文章的人还浏览了...

本文永久链接码友网 » [C#].NET/C#程序开发获取枚举属性的方法有哪些呢?

发布于: 2018-02-27 23:00:00
分享扩散:

文章评论

获取验证码