На наибольшем n-битном числе без знака
Давайте сначала посмотрим, что это за число математически.
В двоичном представлении без знака наибольшее n -битное число будет иметь все биты равными 1. Давайте рассмотрим несколько примеров:
1
(2) = 1 =
2 1 - 1
11
(2) = 3 =
2 2 - 1
111
(2) = 7 =
2 3 - 1
:
1………1
(2) =
2 n -1
n
Обратите внимание, что это аналогично и в десятичном формате.Наибольшее трехзначное число:
10
3 - 1 = 1000 - 1 = 999
Таким образом, подзадача поиска наибольшего n -битное число без знака вычисляет 2 n .
При вычислительной мощности 2
Современные цифровые компьютеры могут эффективно вычислять мощность двух, благодаряследующая схема:
2 0 = 1
(2)
2 1 = 10
(2)
2 2 = 100
(2)
2 3 = 1000
(2)
:
2 n = 10………0
(2)
n
То есть 2 n - это просто число, бит которого n установлен в 1, а все остальноеустановите в 0 (помните, что биты нумеруются с нумерацией индексации).
Решение
Объединяя вышеприведенное, мы получаем это простое решение, используя BigInteger
для нашей проблемы:
final int N = 5;
BigInteger twoToN = BigInteger.ZERO.setBit(N);
BigInteger maxNbits = twoToN.subtract(BigInteger.ONE);
System.out.println(maxNbits); // 31
Если шВместо этого мы использовали long
, тогда мы можем написать что-то вроде этого:
// for 64-bit signed long version, N < 64
System.out.println(
(1L << N) - 1
); // 31
Нет операции "set bit n ", определенной для long
, поэтому традиционно сдвиг битовиспользуется вместоНа самом деле, BigInteger
аналог этой техники переключения также возможен:
System.out.println(
BigInteger.ONE.shiftLeft(N).subtract(BigInteger.ONE)
); // 31
См. Также
Дополнительные BigInteger
подсказки
BigInteger
имеют pow
метод для вычисления неотрицательной степени любого произвольного числа.Если вы работаете в модульном кольце, есть также modPow
и modInverse
.
Вы можете индивидуально setBit
, flipBit
или просто testBit
.Вы можете получить общее значение bitCount
, выполнить поразрядно and
с другим BigInteger
и shiftLeft
/ shiftRight
и т. Д.
В качестве бонуса вы также можете вычислить gcd
или проверить, является ли число isProbablePrime
.
ВСЕГДА помните, что BigInteger
, как и String
, является неизменным .Вы не можете вызвать метод для экземпляра и ожидать, что этот экземпляр будет изменен.Вместо этого всегда присваивайте результат , возвращаемый методом, вашим переменным.