C#Enum.HasFlag与按位AND运算符检查 [英] C# Enum.HasFlag vs. Bitwise AND Operator Check

查看:508
本文介绍了C#Enum.HasFlag与按位AND运算符检查的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如果您有用于位标志的enum,即

If you have an enum that is used for bit flags, i.e.,

[Flags]
internal enum _flagsEnum : byte
{
    None = 0,           //00000000
    Option1 = 1,        //00000001
    Option2 = 1 << 1,   //00000010
    Option3 = 1 << 2,   //00000100
    Option4 = 1 << 3,   //00001000
    Option5 = 1 << 4,   //00010000
    Option6 = 1 << 5,   //00100000
    Option7 = 1 << 6,   //01000000
    Option8 = 1 << 7,   //10000000
    All = Byte.MaxValue,//11111111
}

_flagsEnum myFlagsEnum = _flagsEnum.None;

做起来快吗?

bool hasFlag = myFlagsEnum.HasFlag(_flagsEnum.Option1);

或要做..

bool hasFlag = myFlagsEnum & _flagsEnum.Option1 != 0

如果检查多个标志之间存在性能差异,则也要考虑到这一点.

If there's a performance difference between checking multiple flags, then take that into account as well.

通常我会检查参考源,但是在这种情况下,Enum.HasFlags只是转到外部InternalHasFlags,所以我不知道它在做什么.

Normally I'd check out the reference source, but in this case Enum.HasFlags just goes to an extern InternalHasFlags, so I have no idea what it's doing.

推荐答案

使用HasFlag会降低性能,因为该实现会验证您传递的enum值与该标志的类型相同.

There is a performance cost to using HasFlag, because the implementation verifies that the enum value that you pass is of the same type as the flag.

由于没有这种区别,因此对实现进行了高度优化,以避免将较短的类型(例如byte)提升为int:

With this difference out of the way, the implementation is highly optimized to avoid promoting shorter types, such as byte, to int:

switch (pMTThis->GetNumInstanceFieldBytes()) {
case 1:
    cmp = ((*(UINT8*)pThis & *(UINT8*)pFlags) == *(UINT8*)pFlags);
    break;
case 2:
    cmp = ((*(UINT16*)pThis & *(UINT16*)pFlags) == *(UINT16*)pFlags);
    break;
case 4:
    cmp = ((*(UINT32*)pThis & *(UINT32*)pFlags) == *(UINT32*)pFlags);
    break;
case 8:
    cmp = ((*(UINT64*)pThis & *(UINT64*)pFlags) == *(UINT64*)pFlags);
    break;
default:
    // should not reach here.
    UNREACHABLE_MSG("Incorrect Enum Type size!");
    break;
}

ReflectionEnum::InternalHasFlag的来源可以在此处找到.

尽管成本相对较高,但除了最极端的情况外,这无关紧要.我建议保留它,除非您的探查器指出此调用是程序中的最大瓶颈.

Although the cost is relatively high, it is unlikely to matter, except for the most extreme situations. I would recommend keeping it, unless your profiler points to this call as a largest bottleneck in your program.

这篇关于C#Enum.HasFlag与按位AND运算符检查的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆