C# 数字枚举值作为字符串
Posted
技术标签:
【中文标题】C# 数字枚举值作为字符串【英文标题】:C# numeric enum value as string 【发布时间】:2011-03-27 13:26:13 【问题描述】:我有以下枚举:
public enum Urgency
VeryHigh = 1,
High = 2,
Routine = 4
我可以像这样获取 枚举“值”作为字符串:
((int)Urgency.Routine).ToString() // returns "4"
注意:这不同于:
Urgency.Routine.ToString() // returns "Routine"
(int)Urgency.Routine // returns 4
有没有一种方法可以创建扩展类或静态实用程序类,以提供一些语法糖? :)
【问题讨论】:
您能更准确地了解您要查找的内容吗? 即enumValue.ToValueString() == int 值? 底层 int 值 - 但作为字符串(而不是作为字符串的枚举)而不是记住转换为 int 然后转换为字符串的古老语法,而是一个静态类,其方法采用any 枚举值会使其更易于使用。我怀疑该语言可能不支持我所追求的。 .. 认为我做了你想要的。 【参考方案1】:一个简单的方法
((Urgency)4).ToString() // returns "Routine"
【讨论】:
【参考方案2】:很棒的东西...我现在为我的项目添加了一个扩展方法
public static class EnumExtensions
public static string NumberString(this Enum enVal)
return enVal.ToString("D");
现在我可以通过调用 Urgency.Routine.NumberString();
来获取 int 值 - 作为字符串 - 感谢 Frankentosh 和 Jon :)
【讨论】:
【参考方案3】:为了获得更多“人类可读”的枚举描述(例如,您的示例中的“非常高”而不是“非常高”),我使用如下属性修饰了枚举值:
public enum MeasurementType
Each,
[DisplayText("Lineal Metres")]
LinealMetre,
[DisplayText("Square Metres")]
SquareMetre,
[DisplayText("Cubic Metres")]
CubicMetre,
[DisplayText("Per 1000")]
Per1000,
Other
public class DisplayText : Attribute
public DisplayText(string Text)
this.text = Text;
private string text;
public string Text
get return text;
set text = value;
然后,使用这样的扩展方法:
public static string ToDescription(this Enum en)
Type type = en.GetType();
MemberInfo[] memInfo = type.GetMember(en.ToString());
if (memInfo != null && memInfo.Length > 0)
object[] attrs = memInfo[0].GetCustomAttributes(
typeof(DisplayText),
false);
if (attrs != null && attrs.Length > 0)
return ((DisplayText)attrs[0]).Text;
return en.ToString();
然后你就可以打电话了
myEnum.ToDescription()以将您的枚举显示为更具可读性的文本。
【讨论】:
我也做过类似的事情,但通常只是依赖于骆驼套管的约定。虽然没有按照问题的要求做。 谢谢 - 但不返回 int 值 - 作为字符串 :) 您没有添加DisplayText
属性的声明。可以加一下吗?
谢谢斯图尔特。它现在正在工作。不幸的是,我不能给你多个 +1,所以我想我之前的一个就足够了。
我认为这可能是一位前同事这样做,因为我多次使用相同的解决方案,甚至调用属性 DisplayText - 尽管我也玩过进一步的装饰枚举所以我通过“GetAttrib如果您愿意,可以使扩展方法适用于所有枚举:
public static string ToValueString(this Enum enumValue)
if (enumValue.GetType().GetEnumUnderlyingType() == typeof(int))
return ((int)(object)enumValue).ToString();
else if (enumValue.GetType().GetEnumUnderlyingType() == typeof(byte))
return ((byte)(object)enumValue).ToString();
...
【讨论】:
+1:有趣……但同时看到双重演员有点不寻常。好把戏。 :) 可以使用Enum
而不是T where T : struct
?
你是对的。不知道为什么我认为这在这种情况下很有帮助。更改它以反映您的建议。【参考方案5】:
如果您只想处理这个枚举,请使用 Mark Byer 的解决方案。
对于更通用的解决方案:
public static string NumberString(this Enum enVal)
return Convert.ToDecimal(enVal).ToString("0");
转换为十进制意味着您不需要显式处理 8 种不同的允许的基础整数类型,因为它们都无损地转换为十进制,但彼此之间不转换(ulong 和 long 不会在彼此之间进行无损转换,而是两者都可以处理所有其余的)。这样做可能会更快(尤其是如果您在比较顺序中选择得很好),但会更加冗长,收获相对较小。
编辑:
虽然上面的不如弗兰肯托什,但弗兰肯托什看穿了真正的问题,并且非常雄辩地解决了它。
【讨论】:
【参考方案6】:您应该能够使用 Enums ToString 方法的重载来给它一个格式字符串,这会将枚举的值打印为字符串。
public static class Program
static void Main(string[] args)
var val = Urgency.High;
Console.WriteLine(val.ToString("D"));
public enum Urgency
VeryHigh = 1,
High = 2,
Low = 4
【讨论】:
波什。美丽的简单。让我想删除我的答案! +1 是的,在提供相同的结果和不同的查询方法时,横向思考很好。代码public static string NumberString(this Enum enVal)return enVal.ToString("D");
应该是您的想法并将其转化为所要求的扩展方法。
好东西......请参阅下面的答案
我喜欢这个而不是另一个使用扩展方法的。通过创建扩展方法,您只需为代码添加不必要的依赖项。记住你的代码越少依赖越好!!
应用于多个枚举值(示例):new[] ProductStatus.Open, ProductStatus.Deprecated .Select(s => s.ToString("D"))
【参考方案7】:
稍微反思一下怎么样?应该适用于所有底层类型。
public static class EnumTools
public static string ToRawValueString(this Enum e)
return e
.GetType()
.GetFields(BindingFlags.Public | BindingFlags.Static)
.First(f => f.Name==e.ToString())
.GetRawConstantValue()
.ToString();
然后:
Console.WriteLine(Urgency.High.ToRawValueString()); //Writes "2"
【讨论】:
First() 如果在枚举中没有定义的值匹配该值,则将失败,特别常见于标志枚举并且在其他情况下可能(只要Enum.IsDefined(e.GetType(), e)
返回false)这需要为了在这种情况下更具防御性,然后回退到不会在有效(如果尴尬)值上失败将是使用非反射方法,当您重构时意味着您将删除反射位除非它被证明要快得多。
@Jon :我看不出 Enum 的类型怎么可能不包含它的条目。我错过了什么?编辑:明白了,枚举可能是 ORed 标志。我同意你的评论。
这是最常见的情况。将基础类型的任何值强制转换为枚举类型也是有效的,因此存在 Enum.IsDefined() 以允许捕获可能是方法的无效参数或属性的无效值的情况。【参考方案8】:
您可以为您的特定类型编写扩展方法:
public static class UrgencyExtension
public static string ToIntegerString(this Urgency u)
return ((int)u).ToString();
如下使用:
Urgency u = Urgency.Routine;
string s = u.ToIntegerString();
【讨论】:
以上是关于C# 数字枚举值作为字符串的主要内容,如果未能解决你的问题,请参考以下文章