如何通过EnumMember自定义属性的Value值获取对应枚举项?
实现方案
你可以通过反射读取枚举项的EnumMember特性值做匹配,有两种常用实现方式:
方案1:无第三方依赖的原生实现(带缓存优化性能)
封装通用枚举工具类,一次反射后缓存映射关系,后续调用性能更高,且支持所有加了EnumMember特性的枚举使用:
using System; using System.Collections.Generic; using System.Reflection; using System.Runtime.Serialization; public static class EnumHelper { // 缓存枚举类型到「EnumMember值-枚举项」的映射关系,避免重复反射 private static readonly Dictionary<Type, Dictionary<string, object>> _enumMemberMappingCache = new(); public static T GetEnumByEnumMemberValue<T>(string enumMemberValue) where T : Enum { var enumType = typeof(T); // 缓存不存在则构建映射 if (!_enumMemberMappingCache.TryGetValue(enumType, out var mapping)) { mapping = new Dictionary<string, object>(); foreach (var field in enumType.GetFields(BindingFlags.Public | BindingFlags.Static)) { var attr = field.GetCustomAttribute<EnumMemberAttribute>(); if (attr != null && !string.IsNullOrWhiteSpace(attr.Value)) { mapping[attr.Value] = field.GetValue(null); } } _enumMemberMappingCache[enumType] = mapping; } if (mapping.TryGetValue(enumMemberValue, out var enumItem)) { return (T)enumItem; } // 找不到时的处理逻辑可自行修改,比如返回默认值/抛业务异常 throw new ArgumentException($"{enumType.Name}枚举不存在EnumMember.Value为{enumMemberValue}的项", nameof(enumMemberValue)); } }
你需要的GetDebtType方法直接调用通用工具类即可:
public DebtType GetDebtType(string enumMemberValue) { return EnumHelper.GetEnumByEnumMemberValue<DebtType>(enumMemberValue); }
调用GetDebtType("student_loan")即可得到DebtType.StudentLoan。
方案2:基于Newtonsoft.Json的极简实现
因为你的DebtType已经标记了[JsonConverter(typeof(StringEnumConverter))]特性,直接用Json反序列化即可快速实现,无需自己写反射逻辑:
using Newtonsoft.Json; public DebtType GetDebtType(string enumMemberValue) { // 给字符串套双引号模拟标准Json字符串格式后反序列化 return JsonConvert.DeserializeObject<DebtType>($"\"{enumMemberValue}\""); }
该方法依赖Newtonsoft.Json包,适合已经在项目中引入该包的场景。
内容的提问来源于stack exchange,提问作者kroe761
相关产品推荐
相关产品推荐

