8

我需要在 Java 中将一个字节转换为一个由 4 个布尔值组成的数组。我该怎么办?

4

3 回答 3

12

根据 Michael Petrotta 对您的问题的评论,您需要决定应针对生成的布尔数组测试 8 位字节中的哪些位。出于演示目的,假设您想要最右边的四个位,那么这样的事情应该可以工作:

public static boolean[] booleanArrayFromByte(byte x) {
    boolean bs[] = new boolean[4];
    bs[0] = ((x & 0x01) != 0);
    bs[1] = ((x & 0x02) != 0);
    bs[2] = ((x & 0x04) != 0);
    bs[3] = ((x & 0x08) != 0);
    return bs;
}

此示例中的十六进制值(0x010x02等)是特殊位掩码,在所需位置仅设置了一个位;所以 0x01 只设置了最右边的位,0x08 只设置了从右数第四位。通过使用按位与运算符 ( &) 针对这些值测试给定字节,如果设置了该位,您将获得该值,否则为零。如果要检查不同的位,而不是最右边的四个,则必须创建不同的位掩码。

于 2010-06-17T00:53:54.050 回答
5

关于规范

其他人提出了一个非常有效的观点:在 Java 中,Byte.SIZE == 8. 也就是说,a 中有 8 位byte。您需要定义如何将 8 位映射为 4 个boolean值;否则我们只能猜测你想要做什么。


BitSet

但是,无论您如何进行此映射,它都不太可能boolean[]是最好的表示。Ajava.util.BitSet可能会更好。这是一个例子:

import java.util.*;
public class BitSetExample {
    static BitSet toBitSet(byte b) {
        BitSet bs = new BitSet(Byte.SIZE);
        for (int i = 0; i < Byte.SIZE; i++) {
            if (((b >> i) & 1) == 1) {
                bs.set(i);
            }
        }
        return bs;
    }
    public static void main(String[] args) {
        BitSet bs = toBitSet((byte) 10);
        System.out.println(bs); // prints "{1, 3}"
        System.out.println(bs.get(3)); // prints "true"
        System.out.println(bs.get(2)); // prints "false"

        byte b = 25;
        System.out.println(toBitSet(b)); // prints "{0, 3, 4}"

        bs.or(toBitSet(b));
        System.out.println(bs); // prints "{0, 1, 3, 4}"
    }
}

上面的代码使用标准位探测技术将 a 转换byte为 a BitSet。请注意,a 的(byte) 10第 1 位和第 3 位已设置(即10 = 2^1 + 2^3,其中^表示求幂)。

该示例还显示了如何对 执行or/set 联合操作BitSet


EnumSet

可能另一种适用的数据结构是一个EnumSet,它是一个Set高度优化的实现enum。这是一个例子:

import java.util.*;
public class EnumSetExample {
    enum Style {
        BOLD, ITALIC, UNDERLINE, BLINKING;
    }
    public static void main(String[] args) {
        EnumSet<Style> myStyle = EnumSet.of(Style.BOLD, Style.UNDERLINE);

        System.out.println(myStyle);
        // prints "[BOLD, UNDERLINE]"

        System.out.println(myStyle.contains(Style.UNDERLINE));
        // prints "true"
        System.out.println(myStyle.contains(Style.BLINKING));
        // prints "false" (thank goodness!)

        myStyle.add(Style.ITALIC);
        System.out.println(myStyle);
        // prints "[BOLD, ITALIC, UNDERLINE]"
    }
}

也可以看看

  • Effective Java 第 2 版,第 32 条:使用EnumSet而不是位域
于 2010-06-17T12:12:47.460 回答
0

作为 maerics 答案的附录,如果需要,您可以通过以下方式将 bool 数组转换回字节:

public static byte byteFromBooleanArray(bool[] _boolArray)
    {
        byte x = 0;
        x += _boolArray[0] ? (byte)1 : (byte)0;
        x += _boolArray[1] ? (byte)2 : (byte)0;
        x += _boolArray[2] ? (byte)4 : (byte)0;
        x += _boolArray[3] ? (byte)8 : (byte)0;

        return x;
    }
于 2019-12-20T20:56:20.950 回答