Почему этот код вызывает NumberFormatException
:
String binStr = "1000000000000000000000000000000000000000000000000000000000000000";
System.out.println(binStr.length());// = 64
System.out.println(Long.parseLong(binStr, 2));
Почему этот код вызывает NumberFormatException
:
String binStr = "1000000000000000000000000000000000000000000000000000000000000000";
System.out.println(binStr.length());// = 64
System.out.println(Long.parseLong(binStr, 2));
1000000000000000000000000000000000000000000000000000000000000000
больше Long.MAX_VALUE
.
См. fooobar.com/questions/400813/...
Забастовкa >
Вместо этого используйте BigInteger(String val, int radix)
.
EDIT:
Хорошо, это ново для меня. Похоже, что Integer.parseInt(binaryIntegerString, 2)
и Long.parseLong(binaryLongString, 2)
анализируют двоичный код как величину знака не как 2'-дополнение.
Потому что это вне диапазона. 1000...000
равно 2 63 но Long
достигает только 2 63 - 1.
Это то же самое для всех Long
, Integer
, Short
и Byte
. Я объясню пример Byte
, потому что он читаем:
System.out.println(Byte.MIN_VALUE); // -128
System.out.println(Byte.MAX_VALUE); // 127
String positive = "1000000"; // 8 binary digits, +128
String negative = "-1000000"; // 8 binary digits, -128
String plus = "+1000000"; // 8 binary digits, +128
Byte.parseByte(positive, 2); //will fail because it bigger than Byte.MAX_VALUE
Byte.parseByte(negative, 2); //won't fail. It will return Byte.MIN_VALUE
Byte.parseByte(plus, 2); //will fail because its bigger than Byte.MAX_VALUE
Цифры интерпретируются без знака, независимо от того, какой из них предоставляется. Если вы хотите отрицательное значение, вы должны иметь знак минуса в начале строки. JavaDoc говорит:
Обозначает строковый аргумент как подписанный long в базе, указанной в второй аргумент. Символы в строке должны быть цифрами указанного значения (как определено, если
Character.digit(char, int)
возвращает неотрицательное значение), за исключением того, что первый символ может знак ASCII минус'-' ('\u002D')
для указания отрицательного значения или знак ASCII plus'+' ('\u002B')
для указания положительного значения. получившееся длинное значение возвращается.
Чтобы получить MAX_VALUE
, нам нужно:
String max = "1111111"; // 7 binary digits, +127
// or
String max2 = "+1111111"; // 7 binary digits, +127
Наибольшее длинное значение на самом деле:
0111111111111111111111111111111111111111111111111111111111111111b = 9223372036854775807
Это потому, что Long.parseLong не может разобрать два представления дополнения. Единственный способ разобрать два двоичных представления двоичного кода в Java SE - BigInteger:
long l = new BigInteger("1000000000000000000000000000000000000000000000000000000000000000", 2).longValue()
это дает ожидаемый -9223372036854775808результат
Это максимально возможный длинный (9223372036854775807 = 2 exp 63 - 1) в двоичном формате. Обратите внимание на L в конце последней цифры.
long largestLong = 0B0111_1111_1111_1111_1111_1111_1111_1111_1111_1111_1111_1111_1111_1111_1111_1111L;