2010-04-30 10 views
12

Ich habe Code auf TryParse enum geschrieben entweder nach Wert oder nach seinem Namen wie unten gezeigt. Wie kann ich diesen Code so erweitern, dass enums mit dem Attribut Flags analysiert werden?Enum.TryParse mit Flags-Attribut

public static bool TryParse<T>(this T enum_type, object value, out T result) 
       where T : struct 
      { 
       return enum_type.TryParse<T>(value, true, out result); 
      } 



public static bool TryParse<T>(this T enum_type, 
object value, bool ignoreCase, out T result) 
     where T : struct 
    { 
     result = default(T); 
     var is_converted = false; 

     var is_valid_value_for_conversion = new Func<T, object, bool, bool>[]{ 
      (e, v, i) => e.GetType().IsEnum, 
      (e, v, i) => v != null, 
      (e, v, i) => Enum.GetNames(e.GetType()).Any(n => String.Compare(n, v.ToString(), i) == 0) || Enum.IsDefined(e.GetType(), v) 
     }; 

     if(is_valid_value_for_conversion.All(rule => rule(enum_type, value, ignoreCase))){ 
      result = (T)Enum.Parse(typeof(T), value.ToString(), ignoreCase); 
      is_converted = true; 
     } 

     return is_converted; 
    } 

Derzeit Dieser Code funktioniert für die folgenden Aufzählungen:

enum SomeEnum{ A, B, C } 
// can parse either by 'A' or 'a' 

enum SomeEnum1 : int { A = 1, B = 2, C = 3 } 
// can parse either by 'A' or 'a' or 1 or "1" 

Ist für nicht:

[Flags] 
enum SomeEnum2 { A = 1, B = 2, C = 4 } // can parse either by 'A' or 'a' 
// cannot parse for A|B 

Dank!

Antwort

0

@ Pop Antwort gab mir einen Hinweis & ich die Regeln in meinem Code überprüfen bearbeitet aussehen:

var is_valid_value_for_conversion = new Func<T, object, bool, bool>[] 
{ 
    (e, v, i) => e.GetType().IsEnum, 
    (e, v, i) => value != null, 
    (e, v, i) => Enum.GetNames(e.GetType()).Any(
       n => String.Compare(n, v.ToString(), i) == 0 
       || (v.ToString().Contains(",") && v.ToString().ToLower().Contains(n.ToLower()))) 
       || Enum.IsDefined(e.GetType(), v) 
}; 

der Rest gleich bleibender und es funktioniert für mich

HTH jemand anderes

+1

Sollte der Null-Check nicht deine erste Regel sein? – ChaosPandion

+0

Die erste Prüfung oder Sekunde würde in diesem Fall IMO keinen Unterschied machen, außer ich verpasse etwas, abgesehen davon, dass die Einschränkung auf struct steht, müssen wir prüfen, ob der Aufruf auf einem gültigen Enum-Typ ist, bevor wir prüfen, ob der Wert ist Null – Sunny

16

Ab .NET 4 gibt es eine Enum.TryParse<T> Methode. Es unterstützt Flags Aufzählungen aus der Box:

string x = (SomeEnum2.A | SomeEnum2.B).ToString(); // x == "A, B" 
SomeEnum2 y; 
bool success = Enum.TryParse<SomeEnum2>(x, out y); // y == A|B 
+7

ja TryParse in 4,0 ausgesetzt ist, wurde ich für eine Lösung in 3,5 suchen ... – Sunny

+0

Warum gerade nicht Enum.Parse und WRA Versuchen Sie, einen Block um ihn herum zu fangen? – yoyo

26

Flags Aufzählungen geschrieben verwenden , von .NET Konvention und nicht |. Enum.Parse() funktioniert perfekt, wenn mit '' Strings:

[Flags] 
public enum Flags 
{ 
    A = 1, 
    B = 2, 
    C = 4, 
    D = 8, 
} 

var enumString = (Flags.A | Flags.B | Flags.C).ToString(); 
Console.WriteLine(enumString); // Outputs: A, B, C 
Flags f = (Flags)Enum.Parse(typeof(Flags), enumString); 
Console.WriteLine(f); // Outputs: A, B, C