如果这是一个骗局或者只是一个无聊的问题,我会向前道歉。此外,我将通过我实际找到答案来证明这一点。我对复杂性感到不满意(因为这很无聊))。
问题:
如何在C#2.0中以最简单最优的方式从枚举值数组创建位标志组合
示例代码(不确定这是我们能做的最好的事情):
enum MyEnum
{
Apple = 0,
Apricot = 1,
Breadfruit = 2,
Banana = 4
}
private int ConvertToBitFlags(MyEnum[] flags)
{
string strFlags = string.Empty;
foreach (MyEnum f in flags)
{
strFlags += strFlags == string.Empty ?
Enum.GetName(typeof(MyEnum), f) :
"," + Enum.GetName(typeof(MyEnum), f);
}
return (int)Enum.Parse(typeof(MyEnum), strFlags);
}
答案 0 :(得分:10)
int result = 0;
foreach (MyEnum f in flags)
{
result |= f; // You might need to cast — (int)f.
}
return result;
OTOH,您应该使用FlagsAttribute
来提高类型安全性:
[Flags]
enum MyEnum { ... }
private MyEnum ConvertToBitFlags(MyEnum[] flags)
{
MyEnum result = 0;
foreach (MyEnum f in flags)
{
result |= f;
}
return result;
}
更好的是,通过使用FlagsAttribute
,您可以完全避免使用MyEnum[]
,从而使此方法变得多余。
答案 1 :(得分:2)
这是一个较短的通用扩展版本:
public static T ConvertToFlag<T>(this IEnumerable<T> flags) where T : struct, IConvertible
{
if (!typeof(T).IsEnum)
throw new NotSupportedException($"{typeof(T).ToString()} must be an enumerated type");
return (T)(object)flags.Cast<int>().Aggregate(0, (c, n) => c |= n);
}
使用:
[Flags]
public enum TestEnum
{
None = 0,
Test1 = 1,
Test2 = 2,
Test4 = 4
}
[Test]
public void ConvertToFlagTest()
{
var testEnumArray = new List<TestEnum> { TestEnum.Test2, TestEnum.Test4 };
var res = testEnumArray.ConvertToFlag();
Assert.AreEqual(TestEnum.Test2 | TestEnum.Test4, res);
}