Например, биты в байте B
: 10000010
как я могу присвоить биты строке str
буквально, то есть str = "10000010"
.
редактировать
Я прочитал байт из двоичного файла и сохранил его в массиве байтов B
. Пользуюсь System.out.println(Integer.toBinaryString(B[i]))
. проблема в
(a) когда биты начинаются с (крайнего левого) 1, вывод неверен, потому что он преобразуется B[i]
в отрицательное значение типа int.
(b) если биты начинаются с 0
, вывод игнорируется 0
, например, предположим, что он B[0]
имеет 00000001, вывод 1
вместо00000001
byte
в строку с основанием 2?Boolean
,Byte
,Short
,Char
,Int
, иLong
. stackoverflow.com/a/54950845/501113Ответы:
Использование
Integer#toBinaryString()
:byte b1 = (byte) 129; String s1 = String.format("%8s", Integer.toBinaryString(b1 & 0xFF)).replace(' ', '0'); System.out.println(s1); // 10000001 byte b2 = (byte) 2; String s2 = String.format("%8s", Integer.toBinaryString(b2 & 0xFF)).replace(' ', '0'); System.out.println(s2); // 00000010
ДЕМО .
источник
B
. ПользуюсьSystem.out.println(Integer.toBinaryString(B[i]))
. Когда я использую эти методы, проблема в том, что (а) когда биты начинаются с (крайнего левого) 1, вывод неверен, потому что он преобразуетсяB[i]
в отрицательное значение int. (b) если биты начинаются с 0, вывод игнорируется0
, например, предположим, чтоB[0]
имеет00000001
, вывод1
вместо00000001
byte
в Java - это 8-битное знаковое целое число с дополнением до двух. Его минимальное значение -128 (2 ^ 8), а максимальное значение127
; б) Вы можете легко исправить это, используя этоString.format("%8s", Integer.toBinaryString(b)).replace(' ', '0')
для левой панели получившейся строки с нулями.&
так0xFF
.& 0xFF
основном преобразует asigned byte
вunsigned integer
. Например,-129
как вы сказали, представлен11111111111111111111111110000001
. В этом случае вам в основном нужны первые (наименее значимые) 8 бит, поэтому вы выполняете AND (&
) с помощью0xFF
(00000000000000000000000011111111
), эффективно очищая 1 слева, которые нам не нужны, оставляя только10000001
.Я использовал это. Идея аналогична другим ответам, но нигде не видел точного подхода :)
System.out.println(Integer.toBinaryString((b & 0xFF) + 0x100).substring(1));
0xFF
равно 255 или11111111
(максимальное значение для беззнакового байта).0x100
256, или100000000
&
Сбросы байт в целое число. В этот момент это может быть что угодно от0
-255
(00000000
до11111111
, я исключил первые 24 бита).+ 0x100
и.substring(1)
убедитесь, что в начале есть нули.Я рассчитал время по сравнению с ответом Жоау Силвы , и это более чем в 10 раз быстрее. http://ideone.com/22DDK1 Я не включил ответ Pshemo, так как он неправильно заполняется.
источник
b
есть1
, без+ 0x100
вас просто будет"1"
строка. Добавляя1
, вы получаете100000001
, и если вы возьмете подстроку, игнорируя первый символ, вы получите правильный"00000001"
. Если вы не хотите, чтобы ваша строка была дополнена, вы можете просто использоватьInteger.toBinaryString(b & 0xff)
. В& 0xff
фиксирует негативные / двоек вопросы комплементаЭто то, что вы ищите?
преобразование из строки в байт
byte b = (byte)(int)Integer.valueOf("10000010", 2); System.out.println(b);// output -> -126
преобразование из байта в строку
System.out.println(Integer.toBinaryString((b+256)%256));// output -> "10000010"
Или, как сказал Жоао Силва в своем комментарии, чтобы добавить начало,
0
мы можем отформатировать строку до длины 8 и заменить результирующие ведущие пробелы на ноль, поэтому в случае строки, подобной," 1010"
мы получим"00001010"
System.out.println(String.format("%8s", Integer.toBinaryString((b + 256) % 256)) .replace(' ', '0'));
источник
Вы можете проверить каждый бит байта, а затем добавить к строке 0 или 1. Вот небольшой вспомогательный метод, который я написал для тестирования:
public static String byteToString(byte b) { byte[] masks = { -128, 64, 32, 16, 8, 4, 2, 1 }; StringBuilder builder = new StringBuilder(); for (byte m : masks) { if ((b & m) == m) { builder.append('1'); } else { builder.append('0'); } } return builder.toString(); }
источник
Получить каждый бит байта и преобразовать в строку. Скажем, байт имеет 8 бит, и мы можем получить их один за другим с помощью битового перемещения. Например, мы перемещаем второй бит байта на 6 бит вправо, второй бит в последний бит из 8 бит, затем и (&) с 0x0001, чтобы очистить передние биты.
public static String getByteBinaryString(byte b) { StringBuilder sb = new StringBuilder(); for (int i = 7; i >= 0; --i) { sb.append(b >>> i & 1); } return sb.toString(); }
источник
Этот код продемонстрирует, как java int можно разбить на 4 последовательных байта. Затем мы можем проверить каждый байт с помощью методов Java по сравнению с запросом байтов / битов низкого уровня.
Это ожидаемый результат при запуске кода ниже:
[Input] Integer value: 8549658 Integer.toBinaryString: 100000100111010100011010 Integer.toHexString: 82751a Integer.bitCount: 10 Byte 4th Hex Str: 0 Byte 3rd Hex Str: 820000 Byte 2nd Hex Str: 7500 Byte 1st Hex Str: 1a (1st + 2nd + 3rd + 4th (int(s)) as Integer.toHexString: 82751a (1st + 2nd + 3rd + 4th (int(s)) == Integer.toHexString): true Individual bits for each byte in a 4 byte int: 00000000 10000010 01110101 00011010
Вот код для запуска:
public class BitsSetCount { public static void main(String[] args) { int send = 8549658; System.out.println( "[Input] Integer value: " + send + "\n" ); BitsSetCount.countBits( send ); } private static void countBits(int i) { System.out.println( "Integer.toBinaryString: " + Integer.toBinaryString(i) ); System.out.println( "Integer.toHexString: " + Integer.toHexString(i) ); System.out.println( "Integer.bitCount: "+ Integer.bitCount(i) ); int d = i & 0xff000000; int c = i & 0xff0000; int b = i & 0xff00; int a = i & 0xff; System.out.println( "\nByte 4th Hex Str: " + Integer.toHexString(d) ); System.out.println( "Byte 3rd Hex Str: " + Integer.toHexString(c) ); System.out.println( "Byte 2nd Hex Str: " + Integer.toHexString(b) ); System.out.println( "Byte 1st Hex Str: " + Integer.toHexString(a) ); int all = a+b+c+d; System.out.println( "\n(1st + 2nd + 3rd + 4th (int(s)) as Integer.toHexString: " + Integer.toHexString(all) ); System.out.println("(1st + 2nd + 3rd + 4th (int(s)) == Integer.toHexString): " + Integer.toHexString(all).equals(Integer.toHexString(i) ) ); System.out.println( "\nIndividual bits for each byte in a 4 byte int:"); /* * Because we are sending the MSF bytes to a method * which will work on a single byte and print some * bits we are generalising the MSF bytes * by making them all the same in terms of their position * purely for the purpose of printing or analysis */ System.out.print( getBits( (byte) (d >> 24) ) + " " + getBits( (byte) (c >> 16) ) + " " + getBits( (byte) (b >> 8) ) + " " + getBits( (byte) (a >> 0) ) ); } private static String getBits( byte inByte ) { // Go through each bit with a mask StringBuilder builder = new StringBuilder(); for ( int j = 0; j < 8; j++ ) { // Shift each bit by 1 starting at zero shift byte tmp = (byte) ( inByte >> j ); // Check byte with mask 00000001 for LSB int expect1 = tmp & 0x01; builder.append(expect1); } return ( builder.reverse().toString() ); } }
источник
Integer.toBinaryString((byteValue & 0xFF) + 256).substring(1)
источник
Извините, я знаю, что это немного поздно ... Но у меня есть гораздо более простой способ ... Для двоичной строки:
//Add 128 to get a value from 0 - 255 String bs = Integer.toBinaryString(data[i]+128); bs = getCorrectBits(bs, 8);
getCorrectBits метод:
private static String getCorrectBits(String bitStr, int max){ //Create a temp string to add all the zeros StringBuilder sb = new StringBuilder(); for(int i = 0; i < (max - bitStr.length()); i ++){ sb.append("0"); } return sb.toString()+ bitStr; }
источник
String byteToBinaryString(byte b){ StringBuilder binaryStringBuilder = new StringBuilder(); for(int i = 0; i < 8; i++) binaryStringBuilder.append(((0x80 >>> i) & b) == 0? '0':'1'); return binaryStringBuilder.toString(); }
источник
Вы можете работать с BigInteger, как показано ниже, особенно если у вас 256 бит или больше:
String string = "10000010"; BigInteger biStr = new BigInteger(string, 2); System.out.println("binary: " + biStr.toString(2)); System.out.println("hex: " + biStr.toString(16)); System.out.println("dec: " + biStr.toString(10));
Другой пример, который принимает байты:
String string = "The girl on the red dress."; byte[] byteString = string.getBytes(Charset.forName("UTF-8")); System.out.println("[Input String]: " + string); System.out.println("[Encoded String UTF-8]: " + byteString); BigInteger biStr = new BigInteger(byteString); System.out.println("binary: " + biStr.toString(2)); // binary System.out.println("hex: " + biStr.toString(16)); // hex or base 16 System.out.println("dec: " + biStr.toString(10)); // this is base 10
Результат:
[Input String]: The girl on the red dress. [Encoded String UTF-8]: [B@70dea4e binary: 101010001101000011001010010000001100111011010010111001001101100001000000110111101101110001000000111010001101000011001010010000001110010011001010110010000100000011001000111001001100101011100110111001100101110 hex: 546865206769726c206f6e20746865207265642064726573732e
Вы также можете работать с преобразованием двоичного формата в байтовый
try { System.out.println("binary to byte: " + biStr.toString(2).getBytes("UTF-8")); } catch (UnsupportedEncodingException e) {e.printStackTrace();}
Примечание. Для форматирования строк в двоичном формате вы можете использовать образец ниже.
String.format("%256s", biStr.toString(2).replace(' ', '0')); // this is for the 256 bit formatting
источник
Простой ответ может быть таким:
System.out.println(new BigInteger(new byte[]{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0})); // 0 System.out.println(new BigInteger(new byte[]{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1})); // 1 System.out.println(new BigInteger(new byte[]{0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0})); // 256 System.out.println(new BigInteger(new byte[]{0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0})); // 65536 System.out.println(new BigInteger(new byte[]{0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0})); // 16777216 System.out.println(new BigInteger(new byte[]{0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0})); // 4294967296 System.out.println(new BigInteger(new byte[]{0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0})); // 1099511627776 System.out.println(new BigInteger(new byte[]{0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0})); // 281474976710656 System.out.println(new BigInteger(new byte[]{0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0})); // 72057594037927936 System.out.println(new BigInteger(new byte[]{0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0})); // 18446744073709551616 System.out.println(new BigInteger(new byte[]{0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0})); // 4722366482869645213696 System.out.println(new BigInteger(new byte[]{1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0})); // 1208925819614629174706176 System.out.println(Long.MAX_VALUE); // 9223372036854775807
источник
Все мы знаем, что Java не предоставляет ничего подобного ключевому слову unsigned. Более того,
byte
примитив в соответствии со спецификацией Java представляет собой значение между−128
и127
. Например, еслиbyte
естьcast
наint
Java будет интерпретировать первый ,bit
какsign
и расширение использования знака.Тогда как преобразовать байт больше, чем
127
в его двоичное строковое представление ??Ничто не мешает вам рассматривать
byte
просто как 8-битные и интерпретировать эти биты как значения между0
и255
. Кроме того, вы должны помнить, что вы ничего не можете сделать, чтобы навязать свою интерпретацию чужому методу. Если метод принимает abyte
, тогда этот метод принимает значение между−128
и,127
если явно не указано иное.Итак, лучший способ решить эту проблему - преобразовать
byte
значение вint
значение путем вызоваByte.toUnsignedInt()
метода или преобразования его какint
примитива(int) signedByte & 0xFF
. Вот вам пример:public class BinaryOperations { public static void main(String[] args) { byte forbiddenZeroBit = (byte) 0x80; buffer[0] = (byte) (forbiddenZeroBit & 0xFF); buffer[1] = (byte) ((forbiddenZeroBit | (49 << 1)) & 0xFF); buffer[2] = (byte) 96; buffer[3] = (byte) 234; System.out.println("8-bit header:"); printBynary(buffer); } public static void printBuffer(byte[] buffer) { for (byte num : buffer) { printBynary(num); } } public static void printBynary(byte num) { int aux = Byte.toUnsignedInt(num); // int aux = (int) num & 0xFF; String binary = String.format("%8s', Integer.toBinaryString(aux)).replace(' ', '0'); System.out.println(binary); } }
Выход
источник
Еще один совет для тех, кому нужно массово преобразовывать байты в двоичные строки: используйте таблицу поиска вместо того, чтобы все время использовать эту операцию String. Это намного быстрее, чем снова и снова вызывать функцию convert.
public class ByteConverterUtil { private static final String[] LOOKUP_TABLE = IntStream.range(0, Byte.MAX_VALUE - Byte.MIN_VALUE + 1) .mapToObj(intValue -> Integer.toBinaryString(intValue + 0x100).substring(1)) .toArray(String[]::new); public static String convertByte(final byte byteValue) { return LOOKUP_TABLE[Byte.toUnsignedInt(byteValue)]; } public static void main(String[] args){ System.out.println(convertByte((byte)0)); //00000000 System.out.println(convertByte((byte)2)); //00000010 System.out.println(convertByte((byte)129)); //10000001 System.out.println(convertByte((byte)255)); //11111111 } }
источник
Просто догадываюсь, но если у вас есть Byte, то не могли бы вы просто вызвать toString () для объекта, чтобы получить значение? Или взглянув на api , используя byteValue ()?
источник