Feedback

C# - Enum-Extension - Flag in einem Bitfeld gesetzt?

Veröffentlicht von am 30.11.2009
(2 Bewertungen)
Wer hat nicht schon oft mit Code ähnlich dem Folgenden überprüfen müssen, ob in einem Bitfeld ein bestimmtes Flag gesetzt ist:

if ((FlagA & bitfeld) == FlagA)) { ... }

Die folgenden Extensions erweitern jedes Enum mit der Extension-Methode "Contains". Damit lässt sich nun obiger Code einfacher schreiben:

if (bitfeld.Contains(FlagA)) { ... }

Die generische Variante dieser Methode überprüft zudem, ob das Enum mit dem "Flags"-Attribut gekennzeichnet wurde. :

if (bitfeld.Contains<FlaggedEnum>(FlagA)) { ... }
GFU-Schulungen  [Anzeige]

Angular mit ASP.NET Core für .NET-Entwickler

.NET ist Ihnen vertraut, als Entwickler verfügen Sie über einschlägige Kenntnisse. In diesem Kurs lernen Sie nun, Angular in .NET-Umgebungen einzusetzen. Sie verstehen das Konzept von Angular und integrieren das clientseitige JS-Framework sicher in.NET-Anwendungen.

Visual Studio Team Foundation Server 2017/2015 (TFS) für Projektmitglieder - Kompakt

Nach Teilnahme an dieser Schulung sind Ihnen die Grundlagen von ALM geläufig. Sie planen und steuern Projekte effizient mit dem Visual Studio Team Foundation Server.

/// <summary>
/// Überprüft, ob in dem Bitfeld en1 das Bitfeld en2 enthalten ist.
/// </summary>
/// <param name="en1">Bitfeld 1</param>
/// <param name="en2">Bitfeld 2</param>
/// <returns><c>True</c>, wenn en2 in en1 enthalten ist, sonst <c>False</c>.</returns>
/// <remarks>Bei dieser überlagerten Version der Methode wird nicht überprüft, ob die beiden Bitfelder gleichen Typs sind.
/// <para>Verwenden Sie daher bitte die generische Version dieser Methode, wenn Sie sicherstellen müssen, dass beide Bitfelder gleichen Typs sind.</para></remarks>
public static bool Contains(this Enum en1, Enum en2) {
	return ((Convert.ToInt32(en1) & Convert.ToInt32(en2)) == Convert.ToInt32(en2));
}

/// <summary>
/// Überprüft, ob in dem Bitfeld en1 das Bitfeld en2 enthalten ist.
/// </summary>
/// <typeparam name="TFlaggedEnum">Parameter, der den Typ der Bitfelder angibt.</typeparam>
/// <param name="en1">Bitfeld 1</param>
/// <param name="en2">Bitfeld 2</param>
/// <returns><c>True</c>, wenn en2 in en1 enthalten ist, sonst <c>False</c>.</returns>
public static bool Contains<TFlaggedEnum>(this Enum en1, Enum en2) {
	if (!(Attribute.IsDefined(typeof(TFlaggedEnum), typeof(FlagsAttribute)))) return false;
	if ((en1.GetType().ToString() != en2.GetType().ToString())) return false;
	if ((en1.GetType().ToString() != typeof(TFlaggedEnum).ToString())) return false;
	return ((Convert.ToInt32(en1) & Convert.ToInt32(en2)) == Convert.ToInt32(en2));
}
Abgelegt unter Enum, Extension, Generics, Bitfeld.

1 Kommentare zum Snippet

T.Östreich schrieb am 08.12.2009:
Verbesserungsvorschlag:

public static bool IsSet<TEnum>(this TEnum value, TEnum flag) where TEnum : struct
{
if (!typeof(TEnum).IsEnum)
throw new ArgumentException("TEnum must be an enumerated type");

long valueBase = Convert.ToInt64(value);
long flagBase = Convert.ToInt64(flag);
return (valueBase & flagBase) == flagBase;
}


Test:

/// <summary>
///Ein Test für "IsSet"
///</summary>
public void IsSetTestHelper<TEnum>(TEnum v, TEnum flag, bool expected)
where TEnum : struct
{
bool actual = v.IsSet(flag);
Assert.AreEqual(expected, actual);
}

[TestMethod()]
public void IsSetTest()
{
Test t1 = Test.blue;
Test t2 = Test.green;
Test t3 = Test.blue | Test.red;
IsSetTestHelper<Test>(t1, Test.blue, true);
IsSetTestHelper<Test>(t2, Test.green, true);
IsSetTestHelper<Test>(t3, Test.red, true);
IsSetTestHelper<Test>(t3, Test.red | Test.green, false);
IsSetTestHelper<Test>(t3, Test.blue | Test.red, true);
}

[Flags]
enum Test
{
red = 1,
green = 2,
blue= 4
}
 

Logge dich ein, um hier zu kommentieren!