Как я могу итерации битов в массиве байтов?
Биты Java Iterate в байт-массиве
Ответ 1
Вам нужно написать собственную реализацию Iterable<Boolean>
, которая взяла массив байтов, а затем создала значения Iterator<Boolean>
, которые запоминали текущий индекс в массиве байтов и текущий индекс в текущем байте. Тогда полезный метод, подобный этому, пригодится:
private static Boolean isBitSet(byte b, int bit)
{
return (b & (1 << bit)) != 0;
}
(где bit
находится в диапазоне от 0 до 7). Каждый раз, когда вы вызывали next()
, вам нужно было увеличивать свой битовый индекс в текущем байте и увеличивать байтовый индекс в массиве байтов, если вы достигли "девятого бита".
Это не очень сложно - но немного боль. Дайте мне знать, если вам нужна примерная реализация...
Ответ 2
public class ByteArrayBitIterable implements Iterable<Boolean> {
private final byte[] array;
public ByteArrayBitIterable(byte[] array) {
this.array = array;
}
public Iterator<Boolean> iterator() {
return new Iterator<Boolean>() {
private int bitIndex = 0;
private int arrayIndex = 0;
public boolean hasNext() {
return (arrayIndex < array.length) && (bitIndex < 8);
}
public Boolean next() {
Boolean val = (array[arrayIndex] >> (7 - bitIndex) & 1) == 1;
bitIndex++;
if (bitIndex == 8) {
bitIndex = 0;
arrayIndex++;
}
return val;
}
public void remove() {
throw new UnsupportedOperationException();
}
};
}
public static void main(String[] a) {
ByteArrayBitIterable test = new ByteArrayBitIterable(
new byte[]{(byte)0xAA, (byte)0xAA});
for (boolean b : test)
System.out.println(b);
}
}
Ответ 3
Оригинал:
for (int i = 0; i < byteArray.Length; i++)
{
byte b = byteArray[i];
byte mask = 0x01;
for (int j = 0; j < 8; j++)
{
bool value = b & mask;
mask << 1;
}
}
Или используя идиомы Java
for (byte b : byteArray ) {
for ( int mask = 0x01; mask != 0x100; mask <<= 1 ) {
boolean value = ( b & mask ) != 0;
}
}
Ответ 4
Альтернативой может быть использование BitInputStream, как тот, который вы можете найти здесь и написать код следующим образом:
BitInputStream bin = new BitInputStream(new ByteArrayInputStream(bytes));
while(true){
int bit = bin.readBit();
// do something
}
bin.close();
(Примечание. Для краткости код не содержит процедуры EOFException или IOException.)
Но я бы пошел с вариантом Jon Skeets и сделать это сам.
Ответ 5
Я знаю, возможно, не самый "крутой" способ сделать это, но вы можете извлечь каждый бит следующим кодом.
int n = 156;
String bin = Integer.toBinaryString(n);
System.out.println(bin);
char arr[] = bin.toCharArray();
for(int i = 0; i < arr.length; ++i) {
System.out.println("Bit number " + (i + 1) + " = " + arr[i]);
}
10011100
Бит № 1 = 1
Бит № 2 = 0
Бит номер 3 = 0
Бит № 4 = 1
Бит № 5 = 1
Бит номер 6 = 1
Бит номер 7 = 0
Бит номер 8 = 0
Ответ 6
Вы можете выполнять итерацию по байтовому массиву, и для каждого байта используют побитовые операторы для повторения своих битов.
Ответ 7
Мне понадобилось немного потоковой передачи в моем приложении. Здесь вы можете найти мою реализацию BitArray. Это не настоящий шаблон итератора, но вы можете запросить 1-32 бита из массива потоковым способом. Существует также альтернативная реализация BitReader позже в файле.