我想在Enum中检查传递代码是否存在于任何枚举中。问题是我的枚举定义如下,使用代码属性。
public enum TestEnum
{
None,
[Code("FMNG")]
FunctionsManagement,
[Code("INST_MAST_MGT")]
MasterInstManagement
}
[AttributeUsage(AttributeTargets.Field, AllowMultiple = false)]
public class CodeAttribute : Attribute
{
readonly string _code;
public string Code
{
get
{
return _code;
}
}
public CodeAttribute(string code)
{
_code = code;
}
}
现在,我有可用的字符串(例如“FMNG”),我想在枚举中搜索枚举存在,并且传递的字符串将存在于枚举属性中。
如何使用或传递字符串来检查/获取枚举?我尝试使用Enum.IsDefined(typeof(ActivityEnum), "FMNG")
但它没有使用枚举的属性。
答案 0 :(得分:1)
这是一个通用函数:
public static object ToEnum(string codeToFind, Type t)
{
foreach (var enumValue in Enum.GetValues(t))
{
CodeAttribute[] codes = (CodeAttribute[])(enumValue.GetType().GetField(enumValue.ToString()).
GetCustomAttributes(typeof(CodeAttribute), false));
if (codes.Length > 0 && codes[0].Code.Equals(codeToFind, StringComparison.InvariantCultureIgnoreCase) ||
enumValue.ToString().Equals(codeToFind, StringComparison.InvariantCultureIgnoreCase))
return enumValue;
}
return null;
}
用法:var test = ToEnum("INST_MAST_MGT", typeof(TestEnum));
如果找到定义的Enum
属性或Code
参数等于Enum的值ToString,则上述函数将返回codeToFind
值,您可以根据需要调整它。 / p>
答案 1 :(得分:1)
完全取消该属性并为代码创建静态字典也可能是一个想法:
static Dictionary<string, TestEnum> codeLookup = new Dictionary<string, TestEnum>() {
{ "FMNG" , TestEnum.FunctionsManagement },
{ "INST_MAST_MGT", TestEnum.MasterInsManagement } };
然后就这样做
bool isDefined = codeLookup.ContainsKey("FMNG");
这可能比每次循环属性时使用反射更快,但这取决于您的需求
答案 2 :(得分:0)
public TestEnum GetEnumByAttributeName(string attributeName)
{
foreach (var item in Enum.GetNames(typeof(TestEnum)))
{
var memInfo = typeof(TestEnum).GetMember(item);
var attributes = memInfo[0].GetCustomAttributes(typeof(CodeAttribute), false);
if (attributes.Count()> 0 && ((CodeAttribute)attributes[0]).Code == attributeName)
return (TestEnum)Enum.Parse(typeof(TestEnum), item);
}
return TestEnum.None;
}
答案 3 :(得分:0)
您可以使用此方法:
public static T GetEnumValueByAttributeString<T>(string code) where T : struct
{
if (!typeof(T).IsEnum)
throw new ArgumentException("T should be an enum");
var matches = typeof(T).GetFields().Where(f =>
((CodeAttribute[])(f.GetCustomAttributes(typeof(CodeAttribute), false))).Any(c => c.Code == code)
).ToList();
if (matches.Count < 1)
throw new Exception("No match");
if (matches.Count > 1)
throw new Exception("More than one match");
return (T)(matches[0].GetValue(null));
}
就像你看到的那样,它检查你带来的字符串是否含糊不清。像这样使用它:
var testEnum = GetEnumValueByAttributeString<TestEnum>("FMNG");
如果性能问题,您可能需要初始化并保留所有“翻译”的Dictionary<string, T>
,以便快速查找。
答案 4 :(得分:0)
我在下面找到了通用方法:
public static T GetEnumValueFromDescription<T>(string description)
{
var type = typeof(T);
if (!type.IsEnum)
throw new ArgumentException();
FieldInfo[] fields = type.GetFields();
var field = fields.SelectMany(f => f.GetCustomAttributes(
typeof(CodeAttribute), false), (
f, a) => new { Field = f, Att = a })
.Where(a => ((CodeAttribute)a.Att)
.Code == description).SingleOrDefault();
return field == null ? default(T) : (T)field.Field.GetRawConstantValue();
}