有谁知道如何将枚举值转换为字符串?
示例:
private static void PullReviews(string action, HttpContext context)
{
switch (action)
{
case ProductReviewType.Good.ToString():
PullGoodReviews(context);
break;
case ProductReviewType.Bad.ToString():
PullBadReviews(context);
break;
}
}
编辑:
尝试使用ToString()时;编译器抱怨因为case语句期望一个常量。我也知道ToString()是用intellisense中的一行删除的
答案 0 :(得分:39)
是的,您可以使用.ToString()
获取枚举的字符串值,但不能在switch语句中使用.ToString()
。 Switch语句需要常量表达式,而.ToString()直到运行时才会计算,因此编译器会抛出错误。
要获得所需的行为,只需对方法稍作更改,就可以使用enum.Parse()
将action
字符串转换为枚举值,然后切换该枚举值。从.NET 4开始,您可以使用Enum.TryParse()
并预先进行错误检查和处理,而不是在交换机体中进行。
如果是我,我会将字符串解析为枚举值并打开它,而不是打开字符串。
private static void PullReviews(string action, HttpContext context)
{
ProductReviewType review;
//there is an optional boolean flag to specify ignore case
if(!Enum.TryParse(action,out review))
{
//throw bad enum parse
}
switch (review)
{
case ProductReviewType.Good:
PullGoodReviews(context);
break;
case ProductReviewType.Bad:
PullBadReviews(context);
break;
default:
//throw unhandled enum type
}
}
答案 1 :(得分:13)
你正在倒退。不要尝试使用动态字符串作为案例标签(你不能),而是将字符串解析为枚举值:
private static void PullReviews(string action, HttpContext context)
{
// Enum.Parse() may throw if input is invalid, consider TryParse() in .NET 4
ProductReviewType actionType =
(ProductReviewType)Enum.Parse(typeof(ProductReviewType), action);
switch (actionType)
{
case ProductReviewType.Good:
PullGoodReviews(context);
break;
case ProductReviewType.Bad:
PullBadReviews(context);
break;
default: // consider a default case for other possible values...
throw new ArgumentException("action");
}
}
编辑:原则上,您可以只比较switch语句中的硬编码字符串(见下文),但这是最不可取的方法,因为当您更改传入方法的值时它会简单地中断,或枚举的定义。我正在添加这个,因为值得知道字符串可以用作案例标签,只要它们是编译时文字。动态值不能用作案例,因为编译器不知道它们。
// DON'T DO THIS...PLEASE, FOR YOUR OWN SAKE...
switch (action)
{
case "Good":
PullGoodReviews(context);
break;
case "Bad":
PullBadReviews(context);
break;
}
答案 2 :(得分:5)
public enum Color
{
Red
}
var color = Color.Red;
var colorName = Enum.GetName(color.GetType(), color); // Red
编辑:或许你想要......
Enum.Parse(typeof(Color), "Red", true /*ignorecase*/); // Color.Red
Enum没有TryParse,所以如果你期望错误,你必须使用try / catch:
try
{
Enum.Parse(typeof(Color), "Red", true /*ignorecase*/);
}
catch( ArgumentException )
{
// no enum found
}
答案 3 :(得分:2)
这段代码可行。
private enum ProductReviewType{good, bad};
private static void PullReviews(string action)
{
string goodAction = Enum.GetName(typeof(ProductReviewType), ProductReviewType.good);
string badAction = Enum.GetName(typeof(ProductReviewType), ProductReviewType.bad);
if (action == goodAction)
{
PullGoodReviews();
}
else if (action == badAction)
{
PullBadReviews();
}
}
public static void PullGoodReviews()
{
Console.WriteLine("GOOD Review!");
}
public static void PullBadReviews()
{
Console.WriteLine("BAD Review...");
}
由于解析后的字符串不是常量,因此Switch语句不能使用它。 在VS2005中编译
您可以使用另一个临时变量来保存枚举类的类型,这可以提高性能。
答案 4 :(得分:1)
我建议你走另一条路 - 尝试尽可能多地使用实际的枚举值(通过将字符串转换为枚举值,只要你能),而不是通过应用程序周围的字符串:
ProductReviewType actionType = (ProductReviewType)Enum.Parse(typeof(ProductReviewType), val);
// You might want to add some error handling here.
PullReviews(actionType);
private static void PullReviews(ProductReviewType action, HttpContext context)
{
switch (action)
{
case ProductReviewType.Good:
PullGoodReviews(context);
break;
case ProductReviewType.Bad:
PullBadReviews(context);
break;
}
}
请注意,我已将方法签名更改为接受ProductReviewType
参数;这清楚地说明了你的方法实现其逻辑所需的实际内容,并且符合我的原始观点,即你应该尽量不要传递字符串。
答案 5 :(得分:1)
这只是为了它的乐趣,但是如果你使用了代表词典呢?我意识到你有一个完全不同的方法,但字典化实际上可能更适合你想要完成的事情,特别是因为它提供了高度的模块化,而不是mondo-switch结构(尽管我必须承认,你的枚举只有2个成员所以它是一个有争议的问题)。无论如何,我只是想以不同的方式做事......
基于字典的方法看起来像这样:
namespace ConsoleApplication1
{
public enum ProductReviewType
{
Good,
Bad
}
public static class StringToEnumHelper
{
public static ProductReviewType ToProductReviewType(this string target)
{
// just let the framework throw an exception if the parse doesn't work
return (ProductReviewType)Enum.Parse(
typeof(ProductReviewType),
target);
}
}
class Program
{
delegate void ReviewHandler(HttpContext context);
static readonly Dictionary<ProductReviewType, ReviewHandler>
pullReviewOperations =
new Dictionary<ProductReviewType, ReviewHandler>()
{
{ProductReviewType.Good, new ReviewHandler(PullGoodReviews)},
{ProductReviewType.Bad, new ReviewHandler(PullBadReviews)}
};
private static void PullGoodReviews(HttpContext context)
{
// actual logic goes here...
Console.WriteLine("Good");
}
private static void PullBadReviews(HttpContext context)
{
// actual logic goes here...
Console.WriteLine("Bad");
}
private static void PullReviews(string action, HttpContext context)
{
pullReviewOperations[action.ToProductReviewType()](context);
}
static void Main(string[] args)
{
string s = "Good";
pullReviewOperations[s.ToProductReviewType()](null);
s = "Bad";
pullReviewOperations[s.ToProductReviewType()](null);
// pause program execution to review results...
Console.WriteLine("Press enter to exit");
Console.ReadLine();
}
}
}