2010-10-07 9 views
5

Die folgende Lambda-Statement-Anweisung gibt null zurück, wenn ich hoffte, dass sie einen String-Wert zurückgeben würde.Wie kann ich linq verwenden, um zu überprüfen, ob eine flags/bitwise Enumeration einen Typ enthält?

var countryCode = AddressComponents 
    .Where(x => x.AddressType == AddressType.Country) 
    .Select(x => x.ShortName) 
    .SingleOrDefault(); 

jetzt die Address Eigenschaft der aktuellen Instanz enthält ich bin interrigating die folgenden Daten:

AddressType.Political | AddressType.Country

so wird es zwei Werte enthält.

Natürlich funktioniert mein Lambda nicht, weil der Wert von country (nehmen wir an, es ist 1)! = Der Wert von Political bitwise oder Country (nehmen wir an, es ist 1 | 2 == 3).

Irgendwelche Ideen?

Ich mache mir Sorgen, ich brauche etwas wirklich haben fraking hässlich wie ...

((AddressTypes & AddressType.Country) == AddressType.Country)

.. Gedanken?

Antwort

8

.NET 4.0 hat die Enum.HasFlag Methode:

x => x.AddressType.HasFlag(AddressType.Country) 

Wenn Sie nicht auf .NET 4.0 sind, das bitweise AND Sie haben eine gute Wahl. Wenn Sie das Muster nicht mögen, überprüfen Sie UnconstrainedMelody, die für diesen Zweck eine Erweiterungsmethode hat. Alternativ können Sie selbst eine schreiben; Diese Frage wird wahrscheinlich helfen - Anyone know a good workaround for the lack of an enum generic constraint?

+0

ERNST ?!/brb .... HAHAHAH frag mich :) Es tut es auch! Sieg. gewinnen und el-winno-win !!! Wie wäre es, wenn Sie nach ZWEI Flaggen suchen? zB AddressType.Country oder AddressType.Foo? kann HasFlag (AddressType.Country) | AddressType.Foo) funktioniert? * (beachte das einzelne PIPE-Zeichen) * –

+0

@ Pure.Krome: Ja, das sollte funktionieren. Von MSDN: "Die HasFlag-Methode gibt das Ergebnis des folgenden booleschen Ausdrucks zurück: thisInstance And flag = flag" – Ani

5

Ich fordere Vorsicht mit Enum.HasFlag in .NET 4.0. Als ich meine compute-gebundene App mit ANTS 6.0 profilierte, kam diese Funktion ganz oben an. Zurück zu den alten manuellen Bit-Flag-Tests ergab einen Faktor von> 100 Beschleunigung in meinem Fall. Bis dieser BCL Fehler ausgearbeitet ist, berate dich selbst:

using System; 
using System.Diagnostics; 

class Program 
{ 
    [Flags] enum test { flag1 = 1, flag2 = 2, flag4 = 4 } 

    static void Main(string[] args) 
    { 
     Stopwatch s; 
     test t = test.flag4; 

     s = Stopwatch.StartNew(); 
     for (int c=0,i=0; i < 50000000; i++) 
      if (t.HasFlag(test.flag2)) 
       c++; 
     Console.WriteLine(s.ElapsedMilliseconds); // 22837 ms. 

     s = Stopwatch.StartNew(); 
     for (int c=0,i=0; i < 50000000; i++) 
      if ((t & test.flag2) > 0) 
       c++; 
     Console.WriteLine(s.ElapsedMilliseconds); // 172 ms. 
    } 
} 
+0

Nun, das ist interessant .... Ich frage mich, ob Jon + andere davon etwas wissen? –

+0

Leider ist dies wahr, bekannt und hier erklärt - http://www.codeproject.com/Tips/441086/NETs-Enum-HasFlag-and-performance-costs –

Verwandte Themen