2010-03-07 5 views
54

Decir que tengo una enumeración,Enum.Parse(), seguramente una manera más ordenada?

public enum Colours 
{ 
    Red, 
    Blue 
} 

La única forma que veo de analizar ellos está haciendo algo como:

string colour = "Green"; 
var col = (Colours)Enum.Parse(typeOf(Colours),colour); 

Esto lanzará un System.ArgumentException porque "verde" no es un miembro de el Colours enum.

Ahora realmente odio el código de envoltura en try/catch, ¿no hay una manera más clara de hacer esto que no implique iterar a través de cada enum Colours, y hacer una comparación de cadenas en contra de colour?

Respuesta

52

Primero, use Enum.IsDefined(), para evitar caer en un intento/captura. Devolverá un valor booleano de si la entrada es o no un miembro válido de esa enumeración.

+0

Lo que es más, recuerde que los números de secuencia se analizan aunque no en su Enum! Así que recuerda probar TryParse y comprueba si está definido para captar esa peculiaridad. –

6

No, no hay un método de "no tirar" para esto (al estilo TryParse que tienen otras clases).

Sin embargo, fácilmente se podría escribir su propia con el fin de encapsular la lógica try-catch (o el cheque IsDefined) en un método de ayuda por lo que no contamina el código de aplicación:

public static object TryParse(Type enumType, string value, out bool success) 
{ 
    success = Enum.IsDefined(enumType, value); 
    if (success) 
    { 
    return Enum.Parse(enumType, value); 
    } 
    return null; 
} 
39

creo 4.0 que tiene Enum.TryParse

de lo contrario usar un extension method:

public static bool TryParse<T>(this Enum theEnum, string valueToParse, out T returnValue) 
{ 
    returnValue = default(T); 
    int intEnumValue; 
    if (Int32.TryParse(valueToParse, out intEnumValue)) 
    { 
     if (Enum.IsDefined(typeof(T), intEnumValue)) 
     { 
      returnValue = (T)(object)intEnumValue; 
      return true; 
     } 
    } 
    return false; 
} 
+0

Este TryParse es diferente a 4.0 TryParse, valueToParse debe ser un (cadena) ((byte) YourEnum.YourValue)), la fuente lo usa para analizar el número enum de la cadena de consulta url, no puede usarlo para analizar (cadena) YourEnum .YourValue – aeroson

+0

este método personalizado 'bool estático público TryParse (este Enum theEnum, valor de cadenaToParse, out T returnValue)' requiere restricción de parámetro genérico para ser agregado 'bool estático público TryParse (este Enum theEnum, string valueToParse, out T returnValue) donde T: struct' por ejemplo – oleksa

6

Si estoy pa rsing un "trusted" enum, luego uso Enum.Parse().
Por "confiamos en" Quiero decir, sé que SIEMPRE será una enumeración válida sin errores nunca ... nunca!

Pero hay veces en que "nunca se sabe lo que va a obtener", y para esas ocasiones, debe usar un valor de retorno que se puede nulos. Como .net no ofrece esta función, puedes hacer la tuya. Aquí está mi receta:

public static TEnum? ParseEnum<TEnum>(string sEnumValue) where TEnum : struct 
{ 
    TEnum eTemp; 
    TEnum? eReturn = null; 
    if (Enum.TryParse<TEnum>(sEnumValue, out eTemp) == true) 
     eReturn = eTemp; 
    return eReturn; 
} 

Para utilizar este método, lo llaman así:

eColor? SelectedColor = ParseEnum<eColor>("Red"); 

Sólo añadir este método a una clase que se utiliza para almacenar sus otras funciones de utilidad de uso común.

7

Sólo para ampliar en el enlace del cielo a la .Net 4 Enum.TryParse<>, a saber

Enum.TryParse<TEnum>(
    string value, 
    [bool ignoreCase,] 
    out TEnum result 
) 

Esto se puede utilizar de la siguiente manera:

enum Colour 
    { 
     Red, 
     Blue 
    } 

    private void ParseColours() 
    { 
     Colour aColour; 

     // IMO using the actual enum type is intuitive, but Resharper gives 
     // "Access to a static member of a type via a derived type" 
     if (Colour.TryParse("RED", true, out aColour)) 
     { 
      // ... success 
     } 

     // OR, the compiler can infer the type from the out 
     if (Enum.TryParse("Red", out aColour)) 
     { 
      // ... success 
     } 

     // OR explicit type specification 
     // (Resharper: Type argument specification is redundant) 
     if (Enum.TryParse<Colour>("Red", out aColour)) 
     { 
      // ... success 
     } 
    } 
Cuestiones relacionadas