我的标志位有问题。
我有一个int
变量来保存标志。首先,我为该变量设置了一些标志。后来我需要检查该变量中设置了多少个标志。但我不知道这样做。
答案 0 :(得分:78)
检查是否设置了位值:
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)
}
重要的是要注意,除非它表示全部或无(并且不使用按位逻辑进行比较;只使用value == 0
),否则不应将选中的值设置为0,因为任何value & 0
都是总是0。
答案 1 :(得分:33)
另外,请考虑使用EnumSet
代替位字段。另请参阅Bloch, Item 32。
附录:具体example:
枚举集还为传统位标志提供了丰富的,类型安全的替换:
EnumSet.of(Style.BOLD, Style.ITALIC);
特别注意从AbstractSet
和AbstractCollection
继承的便捷方法。
答案 2 :(得分:17)
如果要检查a
是否设置了b
中的所有标志位,可以将其检查为:
(a & b) == b
答案 3 :(得分:9)
我正在使用以下内容:
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
代替安全类型的额外优惠。
答案 4 :(得分:0)
这是我在项目中使用的Utility类
public class FlagUtils {
// ------------------------------------------------------------------------
// TYPES
// ------------------------------------------------------------------------
// ------------------------------------------------------------------------
// STATIC FIELDS
// ------------------------------------------------------------------------
// ------------------------------------------------------------------------
// STATIC METHODS
// ------------------------------------------------------------------------
/**
* Sets the specified flags on the source int
*
* @param source the source int
* @param flag the flags which should be set
*
* @return the set int
*/
public static int setFlag(int source, int flag) {
return source | flag;
}
/**
* Un-sets the specified flags on the source int
*
* @param source the source int
* @param flag the flags which should be set
*
* @return the set int
*/
public static int unsetFlag(int source, int flag) {
return source & ~flag;
}
/**
* Check if the flags are set on the source ints
*
* @param source the source int
* @param flag the flags which should be set
*
* @return the set int
*/
public static boolean isFlagSet(int source, int flag) {
return (source & flag) == flag;
}
/**
* Flibs teh specified bit on the source
*
* @param source the source int
* @param flag the flags which should be set
*
* @return the set int
*/
public static int flip(int source, int flag) {
return source & ~flag;
}
/**
* Returns the masked int
*
* @param source the source int
* @param mask
*
* @return the set int
*/
public static int mask(int source, int mask) {
return source & mask;
}
// ------------------------------------------------------------------------
// FIELDS
// ------------------------------------------------------------------------
// ------------------------------------------------------------------------
// CONSTRUCTORS
// ------------------------------------------------------------------------
// ------------------------------------------------------------------------
// METHODS
// ------------------------------------------------------------------------
// ------------------------------------------------------------------------
// GETTERS / SETTTERS
// ------------------------------------------------------------------------
}