.NET enum.HasFlag() 错误?
.NET enum.HasFlag() bug?
我正在使用以下 .NET 4.5.2 代码:
if (this.ContainsFocus && keyData == (Keys.Tab|Keys.Shift))
{ ... }
为什么当ContainsFocus (bool = true) 和keyData (System.Windows.Forms.Keys) 为Keys.O 时表达式为真 | Keys.Shift?
如您所见,命中断点:
具有以下值:
此错误 (?!) 的解决方法是:
if (this.ContainsFocus && (int)keyData == (int)(Keys.Tab|Keys.Shift))
{ ... }
这不是 HasFlag
的错误,而是它的工作原理。
假设我们有以下值:
var a = (Keys.Tab | Keys.Shift);
var b = (Keys.O | Keys.Shift);
现在我们分析这些值的位(当我们将它们转换为整数时):
a: 10000000001000001
b: 10000000001001111
如果我们调用 a.HasFlag(b)
,我们会得到 false
,因为并非 b 中的每个 1 位都是 a[= 中的 1 32=]也是。但是如果我们调用 b.HasFlag(a)
我们会得到 true
因为 a 的每个 1 位也在 b 中设置。
这就是为什么您需要将值与 a==b
或 a.HasFlag(b) && b.HasFlag(a)
进行比较的原因。然后就可以正常使用了。
不,HasFlag
没有错误。不幸的是,.NET FlagsAttribute
是全有或全无,并且 System.Windows.Forms.Keys
的定义方式使得只有 Keys.Modifiers
可以用作标志。
来自https://msdn.microsoft.com/en-us/library/system.windows.forms.keys%28v=vs.110%29.aspx
The Keys class contains constants for processing keyboard input. The
members of the Keys enumeration consist of a key code and a set of
modifiers combined into a single integer value. In the Win32
application programming interface (API) a key value has two halves,
with the high-order bits containing the key code (which is the same as
a Windows virtual key code), and the low-order bits representing key
modifiers such as the SHIFT, CONTROL, and ALT keys.
因此,您可以使用 HasFlag
检查任何修饰符(Keys.Shift
、Keys.Alt
、Keys.Control
),但不能检查其他任何修饰符。
我正在使用以下 .NET 4.5.2 代码:
if (this.ContainsFocus && keyData == (Keys.Tab|Keys.Shift))
{ ... }
为什么当ContainsFocus (bool = true) 和keyData (System.Windows.Forms.Keys) 为Keys.O 时表达式为真 | Keys.Shift?
如您所见,命中断点:
具有以下值:
此错误 (?!) 的解决方法是:
if (this.ContainsFocus && (int)keyData == (int)(Keys.Tab|Keys.Shift))
{ ... }
这不是 HasFlag
的错误,而是它的工作原理。
假设我们有以下值:
var a = (Keys.Tab | Keys.Shift);
var b = (Keys.O | Keys.Shift);
现在我们分析这些值的位(当我们将它们转换为整数时):
a: 10000000001000001
b: 10000000001001111
如果我们调用 a.HasFlag(b)
,我们会得到 false
,因为并非 b 中的每个 1 位都是 a[= 中的 1 32=]也是。但是如果我们调用 b.HasFlag(a)
我们会得到 true
因为 a 的每个 1 位也在 b 中设置。
这就是为什么您需要将值与 a==b
或 a.HasFlag(b) && b.HasFlag(a)
进行比较的原因。然后就可以正常使用了。
不,HasFlag
没有错误。不幸的是,.NET FlagsAttribute
是全有或全无,并且 System.Windows.Forms.Keys
的定义方式使得只有 Keys.Modifiers
可以用作标志。
来自https://msdn.microsoft.com/en-us/library/system.windows.forms.keys%28v=vs.110%29.aspx
The Keys class contains constants for processing keyboard input. The members of the Keys enumeration consist of a key code and a set of modifiers combined into a single integer value. In the Win32 application programming interface (API) a key value has two halves, with the high-order bits containing the key code (which is the same as a Windows virtual key code), and the low-order bits representing key modifiers such as the SHIFT, CONTROL, and ALT keys.
因此,您可以使用 HasFlag
检查任何修饰符(Keys.Shift
、Keys.Alt
、Keys.Control
),但不能检查其他任何修饰符。