C#枚举 – 针对面具检查标志
我有以下枚举标志:
[Flags] private enum MemoryProtection: uint { None = 0x000, NoAccess = 0x001, ReadOnly = 0x002, ReadWrite = 0x004, WriteCopy = 0x008, Execute = 0x010, ExecuteRead = 0x020, ExecuteReadWrite = 0x040, ExecuteWriteCopy = 0x080, Guard = 0x100, NoCache = 0x200, WriteCombine = 0x400, Readable = (ReadOnly | ReadWrite | ExecuteRead | ExecuteReadWrite), Writable = (ReadWrite | WriteCopy | ExecuteReadWrite | ExecuteWriteCopy) }
现在我有一个枚举实例,我需要检查它是否可读。 如果我使用以下代码:
myMemoryProtection.HasFlag(MemoryProtection.Readable)
它总是在我的情况下返回false,因为我认为HasFlag检查它是否有每个标志。 我需要优雅的东西来避免这样做:
myMemoryProtection.HasFlag(MemoryProtection.ReadOnly) || myMemoryProtection.HasFlag(MemoryProtection.ReadWrite) || myMemoryProtection.HasFlag(MemoryProtection.ExecuteRead) || myMemoryProtection.HasFlag(MemoryProtection.ExecuteReadWrite)
我该怎么做?
你可以改变条件,检查复合enum
是否有标志,而不是检查复合的标志,如下所示:
if (MemoryProtection.Readable.HasFlag(myMemoryProtection)) { ... }
这是一个例子:
MemoryProtection a = MemoryProtection.ExecuteRead; if (MemoryProtection.Readable.HasFlag(a)) { Console.WriteLine("Readable"); } if (MemoryProtection.Writable.HasFlag(a)) { Console.WriteLine("Writable"); }
这打印Readable
。
是的, hasFlag
检查是否设置了每个位字段(标志)。
而不是将Readable
视为包含Read
in the name的所有保护的组合,你可以改变组合吗? 例如
[Flags] private enum MemoryProtection: uint { NoAccess = 0x000, Read = 0x001, Write = 0x002, Execute = 0x004, Copy = 0x008, Guard = 0x010, NoCache = 0x020, ReadOnly = Read, ReadWrite = (Read | Write), WriteCopy = (Write | Copy), // etc. NoAccess = 0x800 }
然后你可以编写如下代码:
myMemoryProtection.HasFlag(MemoryProtection.Read)
尝试按位运算符:
[TestMethod] public void FlagsTest() { MemoryProtection mp = MemoryProtection.ReadOnly | MemoryProtection.ReadWrite | MemoryProtection.ExecuteRead | MemoryProtection.ExecuteReadWrite; MemoryProtection value = MemoryProtection.Readable | MemoryProtection.Writable; Assert.IsTrue((value & mp) == mp); }