C# 应该";或;使用.Net4 Hasflags:enum.HasFlag(AccessRights.Read | AccessRights.Write)

C# 应该";或;使用.Net4 Hasflags:enum.HasFlag(AccessRights.Read | AccessRights.Write),c#,.net-4.0,enums,enum-flags,C#,.net 4.0,Enums,Enum Flags,我正在试用新的HasFlags功能,并想知道以下功能是否有效: enum.HasFlag(AccessRights.Read | AccessRights.Write) 。。。因为它似乎不 DBAccessRights rights = (DBAccessRights)permission.PermissionFlags; if (rights.HasFlag(DBAccessRights.WikiMode)) { // works } if (rights.Ha

我正在试用新的HasFlags功能,并想知道以下功能是否有效:

enum.HasFlag(AccessRights.Read | AccessRights.Write)

。。。因为它似乎不

 DBAccessRights rights = (DBAccessRights)permission.PermissionFlags;
  if (rights.HasFlag(DBAccessRights.WikiMode))
  {
     // works
  }


  if (rights.HasFlag(DBAccessRights.WikiMode | DBAccessRights.CreateNew))
  {
     // Doesn't work    
  }

  DBAccessRights flags = DBAccessRights.WikiMode | DBAccessRights.CreateNew;
  if (rights.HasFlag(flags))
  {
     // Doesn't work
  }

|
运算符是按位或。这意味着如果
Read
为1而
Write
为2,则
Read | Write
的值为3(参见其二进制表示)。因此,只有当
enum
变量同时设置了
Read
Write
时,
HasFlag
才会返回true。

如果给定的值同时具有这两个标志,我希望返回true

如果您想让它测试您的值是否有这些标志中的任何一个,您需要

value.HasFlag(AccessRights.Read) | value.HasFlag(AccessRights.Write)
如果你读起来不够好,你可以看看我的项目。碰巧它已经具有您想要的功能(作为中的扩展方法):

这会让事情变得更清楚,我想。它们也会避免装箱,并且是类型安全的:)

来自:

HasFlag方法返回以下布尔值的结果 表情

thisInstance和flag=flag

对于复杂标志,如
AccessRights.Read | AccessRights.Write
,这将检查是否存在所有“包含的”标志

您可能需要检查是否存在任何标志,在这种情况下,您可以执行以下操作:

myAccessRights & (AccessRights.Read | AccessRights.Write) != 0 

或者,您可以颠倒表达式的顺序:

//returns true - a bit easier on the eye
(AccessRights.Read | AccessRights.Write).HasFlag(myAccessRights)
如果您具有读写访问权限,则返回true。这在功能上相当于:

//also returns true - as per @Ani's answer
myAccessRights & (AccessRights.Read | AccessRights.Write) != 0
编辑


正如注释中所指出的,如果myAccessRights为空,则第一个表达式将返回true;如果myAccessRights不仅仅具有读写功能,则第一个表达式将返回false。

装箱是否解释了文档底部的性能说明?@makerofthings7:可能-很难说清楚。测量框架和我的实现之间的性能差异会很有趣:)@LamonteCristo此方法还必须在取消装箱之前进行类型检查。如果您传递了错误类型的引用,他们希望抛出
ArgumentException
。我想知道拆箱时是否再次进行了类型检查。我们可以检查字节码或C#源代码。如果有,为什么不直接执行(AccessRights.Read | AccessRights.Write).HasFlag(value)?以防任何人想要直接链接到包含
HasAll()的文件
方法
https://github.com/jskeet/unconstrained-melody/blob/master/UnconstrainedMelody/Flags.cs
。我在接受这个和乔恩·斯基特的答案之间左右为难。这是实现我目标的最佳方式。他的回答解释了我做错了什么。如果myAccessRights没有设置不正确的标志,则返回true。但无论如何。与此类似,除非您假设读写是AccessRights中定义的唯一标志,否则它在功能上是不等价的——即使它是真的,您也不应该这样做。如果myAccessRights设置了除读或写之外的任何标志,则第一个表达式将返回false。
//also returns true - as per @Ani's answer
myAccessRights & (AccessRights.Read | AccessRights.Write) != 0