Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Enum.Parse() or Switch

For converting a string to an enum, which of the following ways is better?

  1. This code:

    colorEnum color = (colorEnum)Enum.Parse(typeof(colorEnum), "Green");
    
  2. or this:

    string colorString = ...
    colorEnum color;        
    switch (colorString)
    {
        case "Green":
            color = colorEnum.Green;
            break;
        case "Red":
            color = colorEnum.Red;
            break;
        case "Orange":
            color = colorEnum.Orange;
            break;
        ....
    }
    
like image 754
Nicola Avatar asked Sep 21 '11 08:09

Nicola


3 Answers

You should use the Enum.TryParse, if it fails you can handle the error correctly.

sample:

     ColorsEnum colorValue; 
     if (Enum.TryParse(colorString, out colorValue))        
        if (Enum.IsDefined(typeof(Colors), colorValue) | colorValue.ToString().Contains(","))  
           Console.WriteLine("Converted '{0}' to {1}.", colorString, colorValue.ToString());
        else
           Console.WriteLine("{0} is not an underlying value of the Colors enumeration.", colorString);
     else
        Console.WriteLine("{0} is not a member of the Colors enumeration.", colorString);
like image 63
Peter Avatar answered Nov 07 '22 14:11

Peter


(Warning: includes plug for my own open source library...)

Personally I'd use Unconstrained Melody, which ends up with cleaner and more typesafe code:

ColorEnum color = Enums.ParseName<ColorEnum>(text);

You can use TryParseName if you suspect it may be invalid. Obviously this requires an extra library, but hopefully you'll find other things in there helpful too :)

Enum.TryParse from .NET 4 is better than the other built-in options, but:

  • You won't catch non-enum types at compile time, e.g. Enum.TryParse<int>(...) will still compile; Unconstrained Melody really only allows enum types
  • Enum.TryParse will also parse "1" (or whatever the numeric value is when converted to a string) - if you really only expect names, I think it's better to only accept names

I definitely wouldn't switch on the string values - it means if you rename the enum values, you've got to remember to rename the case value as well.

like image 8
Jon Skeet Avatar answered Nov 07 '22 15:11

Jon Skeet


And what about Enum.TryParse<TEnum> ?

string myColorStr = "red";
colorEnum myColor;
if(!Enum.TryParse<colorEnum>(myColorStr, true, out myColor))
{
    throw new InvalidOperationException("Unknown color " + myColorStr);
}
like image 4
Steve B Avatar answered Nov 07 '22 16:11

Steve B