Check if flag is set in integer variable

若如初见. 提交于 2019-12-06 16:33:34

No it isn't, you should use the bitwise AND operator instead - & and set the flags as binary values - your intuition is correct on that side.

A common trick to setting specific bits is using the shift operator:

int DRAW_REPEAT_X = 0x1 << 0;  //first bit set to 1, others 0
int DRAW_REPEAT_Y = 0x1 << 1;  //second bit set to 1, others 0

and check the int as

if (drawMethod & DRAW_REPEAT_X)  //check it that particular flag is set, ignore others
{
}

For this to work, your flag variables each need to have a single, unique bit set. That bit is the "flag". For constants where it's the bitwise representation that matters, it's much more convenient to use hexadecimal or octal (because these bases are a power of 2) than decimal. So, for example:

enum {
    DRAW_REPEAT_X = 0x01,    /* First bit set */
    DRAW_REPEAT_Y = 0x02,    /* Second bit set */
    DRAW_MIRRORED = 0x04,    /* Third bit set */
};

int drawMethod = DRAW_REPEAT_X | DRAW_REPEAT_Y;  /* Will have both first and second bits set */

Then you use bitwise-and & rather than logical-and && to test the bits. a & b will be non-zero if and only if there is at least one bit that is set in both a and b. In the case of testing for a flag, one of these will have only one bit set - the flag you're interested in - so the result of a & flag will be non-zero if and only if the flag is set in a:

if (drawMethod & DRAW_REPEAT_X) {
  // the user wants me to repeat an image along the x axis
}

if (drawMethod & DRAW_REPEAT_Y) {
  // the user wants me to repeat an image along the x axis
}

The hexadecimal pattern for constants with one bit set is 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, ...

As it stands right now, you aren't using flags so much as having a value that indicates a method. Much better is to use some sort of bits, like this:

int DRAW_REPEAT_X=0x01;
int DRAW_REPEAT_Y=0x02;

And then check the ifs like you are doing now, but with a single &

if (drawMethod & DRAW_REPEAT_X)

Typically, your integers (DRAW_REPEAT_X) should be public static, if you are working with a class architecture. But not knowing if that is the case, I won't include them

Here's a code snippet using the WinAPIs that shows setting two flags to a value, and then checking for the existence of at least one of those flags in that value. It should return 0;

INPUT mip;
mip.type = INPUT_MOUSE;
mip.mi.mouseData = 0;
mip.mi.dwFlags = MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE;

if (mip.mi.dwFlags & (MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_HWHEEL))
    return 0;

If you want to check for an exact value combination, you don't need to use the bitwise operator &, and can do a simple == check.

For example, the updated line near the bottom

INPUT mip;
mip.type = INPUT_MOUSE;
mip.mi.mouseData = 0;
mip.mi.dwFlags = MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE;

if (mip.mi.dwFlags == (MOUSEEVENTF_ABSOLUTE | MOUSEEVENTF_MOVE))
    return 0;
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!