2011-05-20 64 views
38

我有一个标志位的问题。 我有一个int变量来保存标志。首先,我为该变量设置了一些标志。稍后我需要检查在该变量中设置了多少个标志。但我不知道这样做。检查标志位java

回答

65

要检查,看是否有位值设置:

int value = VALUE_TO_CHECK | OTHER_VALUE_TO_CHECK; 

if ((value & VALUE_TO_CHECK) == VALUE_TO_CHECK) 
{ 
    // do something--it was set 
} 

if ((value & OTHER_VALUE_TO_CHECK) == OTHER_VALUE_TO_CHECK) 
{ 
    // also set (if it gets in here, then it was defined in 
    // value, but it does not guarantee that it was set with 
    // OR without other values. To guarantee it's only this 
    // value just use == without bitwise logic) 
} 

需要注意的是,你不应该有一个检查值0,除非它代表全或无(不要使用位逻辑是很重要的以进行比较;仅使用value == 0),因为任何value & 0总是为0.

+0

这里我没有标志(如VALUE_TO_CHECK)。我有另一个包含一些标志的变量。所以我需要找到A包含所有的女巫是否存在于B中。 – Nagaraju 2011-05-20 04:27:35

+2

@Naga raju所以请澄清你的问题。 – EJP 2011-05-20 04:35:31

+1

如果你有一堆标志设置的值:'int A = flag1 | flag3 | flag15;'你想看看它是否具有来自'B'的所有值:'int B = flag3 |在上面的代码中,flag15;',then'B'_is_' VALUE_TO_CHECK':'if(A&B == B)'(忽略可怕的变量名)。另外,由于听起来像你对此感到困惑,你应该参考垃圾回答并购买参考书(由Josh Bloch提供)。这是作为Java开发人员拥有的最好的书。 – pickypg 2011-05-20 04:37:31

30

另外,考虑使用EnumSet而不是位字段。另见Bloch, Item 32

附录:作为一个具体的example

枚举集还提供了丰富的,类型安全的替代传统的位标志:

EnumSet.of(Style.BOLD, Style.ITALIC); 

请特别注意从AbstractSet继承了方便的方法和AbstractCollection

+0

如何使用它来替换位域?我没能跳起来。 – Suragch 2017-02-11 09:20:24

+0

我不确定您遇到问题的位置;更多示例可以在[这里]找到(http://stackoverflow.com/search?tab=votes&q=%5bjava%5d%20EnumSet%20bit%20field)。 – trashgod 2017-02-11 10:18:52

14

如果你想检查是否有a所有标志位b集,您可以检查它为:

(a & b) == b 
7

我使用了以下内容:

public class BitFlags 
{ 
    public static boolean isFlagSet(byte value, byte flags) 
    { 
     return (flags & value) == value; 
    } 

    public static byte setFlag(byte value, byte flags) 
    { 
     return (byte) (flags | value); 
    } 

    public static byte unsetFlag(byte value, byte flags) 
    { 
     return (byte) (flags & ~value); 
    } 
} 

但是,如果不需要它“低级别”,建议使用EnumSets来代替额外的安全类型。