2011-09-19 96 views
30

我不知道一个通​​用的方法为enum标志的所有位设置为1 枚举标志的所有位我只是想有一个enum返回所有的比较,无论其他枚举。如何设置

而这段代码有效;

[Flags] 
public enum SomeRightEnum : uint 
{ 
    CanDoNothing = 0, 
    CanDoSomething = 1 << 0, 
    CanDoSomethingElse = 1 << 1, 
    CanDoYetAnotherThing = 1 << 2, 
    ... 
    DoEverything = 0xFFFFFFFF 
} 

但在上面,因为它是我们UINT设置的“F”的数目的代码,如果它是int这是行不通的。

所以我会感激enum标志的所有位设置为1的通用方法,无论数据类型(i NT,int64uint等)

+1

嗯。枚举的目的是描述相互排斥的选项。你似乎将它们用作一堆位掩码的简写。 –

+1

@AFgone您在枚举权上使用[Flags]属性? –

+1

@Oli枚举上的[Flags]属性是为此设计的。 –

回答

47

最简单的大概是:

enum Foo 
{ 
    blah = 1, 
    .... 
    all = ~0 
} 

对于无符号基于枚举:

enum Foo : uint 
{ 
    blah = 1, 
    .... 
    all = ~0u; 
} 
+0

当我试着这样说它说:“不变的值'-1'不能转换为'uint'” – AFgone

+1

只是演员然后,例如'unchecked((uint)〜0)' – leppie

+0

非常感谢这就是我正在寻找的 – AFgone

3
internal static class Program 
{ 
    private static void Main() 
    { 
     Console.WriteLine(Foo.Everything.HasFlag(Foo.None)); // False 
     Console.WriteLine(Foo.Everything.HasFlag(Foo.Baz)); // True 
     Console.WriteLine(Foo.Everything.HasFlag(Foo.Hello)); // True 
    } 
} 

[Flags] 
public enum Foo : uint 
{ 
    None = 1 << 0, 
    Bar = 1 << 1, 
    Baz = 1 << 2, 
    Qux = 1 << 3, 
    Hello = 1 << 4, 
    World = 1 << 5, 
    Everything = Bar | Baz | Qux | Hello | World 
} 

是这样的,你想要什么?

+0

但这不是其他枚举,当我编辑或删除枚举我不得不改变“一切” – AFgone

5

万一有人疑惑: 我需要做同样的建设WPF一个可绑定enumconverter。
由于我不知道Reflection中的值是什么意思,我需要手动切换值(将它们绑定到复选框pe)
将Flagged enum的值设置为-1以设置所有的位。
如果将其设置为-1,并且取消标记所有值,则不会导致0,因为所有未使用的位都不是未标记的。
这是笏最适合我的情况。

SomeRightEnum someRightEnum = SomeRightEnum.CanDoNothing; 
Type enumType = someRightEnum.GetType(); 
int newValue = 0; 
var enumValues = Enum.GetValues(enumType).Cast<int>().Where(e => e == 1 || e % 2 == 0); 
foreach (var value in enumValues) 
{ 
    newValue |= value; 
} 
Console.WriteLine(newValue); 

或者,如果你想扩展方法:

public static class FlagExtensions 
{ 
    public static TEnum AllFlags<TEnum>(this TEnum @enum) 
     where TEnum : struct 
    { 
     Type enumType = typeof(TEnum); 
     long newValue = 0; 
     var enumValues = Enum.GetValues(enumType); 
     foreach (var value in enumValues) 
     { 
      long v = (long)Convert.ChangeType(value, TypeCode.Int64); 
      if(v == 1 || v % 2 == 0) 
      { 
       newValue |= v; 
      } 
     } 
     return (TEnum)Enum.ToObject(enumType , newValue); 
    } 
} 
+0

使其成为扩展'enum'系统类的名为'AllFlags'的扩展方法。那么它可以整齐地使用'enum。AllFlags(typeof(MyEnum))'no? –

+0

@ v.oddou我用一个返回(不可变)值的通用扩展更新了我的答案。我还删除了一个缺省的非标志值。 – Silvermind

18
[Flags] 
public enum MyEnum 
{ 
    None = 0, 
    First = 1 << 0, 
    Second = 1 << 1, 
    Third = 1 << 2, 
    Fourth = 1 << 3, 
    All = ~(-1 << 4) 
} 
+0

我喜欢这个选项,甚至比我通常的'-1'选项更好。我使用枚举来跟踪哪些任务被请求,并在任务完成时删除标志。然后,我的计划是使用结果作为退出代码。所以这有助于维护任务枚举。 – Schmalls

+1

我更喜欢'所有=〜(〜0 << 4)',因为它更清晰一点。不是每个人都知道'-1'全是'1'。 –

+0

'None'不应该是'-1'?! – akhansari