Java for Beginner
680 subscribers
563 photos
158 videos
12 files
867 links
Канал от новичков для новичков!
Изучайте Java вместе с нами!
Здесь мы обмениваемся опытом и постоянно изучаем что-то новое!

Наш YouTube канал - https://www.youtube.com/@Java_Beginner-Dev

Наш канал на RUTube - https://rutube.ru/channel/37896292/
Download Telegram
Глубокое изучение типа данных long в Java: сравнение с byte, short и int

Тип данных long в Java — это 64-битное целое число со знаком. Он используется, когда диапазона int недостаточно для представления чисел, особенно в финансовых расчётах, временных метках, системах счёта, генерации идентификаторов и других задачах, связанных с большими значениями.

Размер и диапазон

long занимает 8 байт (64 бита) и позволяет представлять значения от -9 223 372 036 854 775 808 до 9 223 372 036 854 775 807. Это примерно ±9 квинтиллионов.

Для сравнения:
byte: 1 байт, от -128 до 127
short: 2 байта, от -32 768 до 32 767
int: 4 байта, от -2.1 млрд до 2.1 млрд


Когда ни byte, ни short, ни даже int не покрывают диапазон значений — long становится необходимостью.

Внутреннее представление

Как и остальные знаковые целые типы в Java, long реализован через дополнительный код (two’s complement). Старший (64-й) бит отвечает за знак: 0 — положительное число или ноль, 1 — отрицательное. Всё остальное аналогично другим типам, но с удвоенным количеством бит по сравнению с int.

Работа с памятью

long — примитивный тип, поэтому:
локальные переменные long хранятся в стеке;
поля объектов — в куче;
память управляется виртуальной машиной Java автоматически: выделяется при создании переменной, освобождается при выходе из области видимости (для локальных) или сборке мусора (для объектов).
Массив
long[] из миллиона элементов потребует 8 МБ памяти, тогда как int[] — всего 4 МБ, а byte[] — 1 МБ. Это важно учитывать при проектировании систем, чувствительных к объёму памяти.

Арифметика и автоматическое повышение типов

Арифметика с long происходит без повышения до int, в отличие от byte и short, которые автоматически продвигаются до int в выражениях. Однако, при использовании int и long в одном выражении, результат будет long.

Пример:
int a = 1_000_000_000;
int b = 3;
long result = a * b; // результат может быть неверным!


Здесь сначала перемножаются два int, а потом результат приводится к long. Чтобы избежать переполнения, нужно один из операндов явно сделать long:
long result = (long) a * b; // безопасно


Переполнение и wraparound

Тип long, несмотря на огромный диапазон, всё равно может переполниться. Если результат выходит за пределы диапазона, он не вызывает исключения, а оборачивается по модулю 2⁶⁴:
long x = Long.MAX_VALUE;
x++;
System.out.println(x); // выведет отрицательное число: Long.MIN_VALUE
Это поведение аналогично тому, что происходит с int, short и byte, но требует повышенного внимания при работе с предельными значениями.


Беззнаковость и побитовая работа

В Java нет беззнакового long. Для имитации поведения 64-битного беззнакового числа можно использовать BigInteger, либо применять побитовые маски и операторы, чтобы интерпретировать старшие биты корректно.

Например:
long l = -1L;
String binary = Long.toBinaryString(l); // все 64 бита — единицы


С Java 8 появилась поддержка методов для unsigned арифметики: Long.divideUnsigned, Long.toUnsignedString и т.п., но сами типы остались только знаковыми.

Сравнение с младшими типами

byte и short — экономны по памяти, но быстро переполняются. Используются в низкоуровневом коде, где важен каждый байт.
int — универсален, безопасен по диапазону для большинства задач.
long — выбор для работы с большими числами, когда int недостаточен.
Однако, использование
long без необходимости может привести к перерасходу памяти — особенно в коллекциях, структурах данных, больших массивах. Используйте long там, где это действительно оправдано.

Особенности и рекомендации

При передаче литералов типа long, добавляйте суффикс L, чтобы избежать ошибочного приведения к int:
long big = 3000000000L; // без 'L' это вызовет переполнение int
Проверяйте выражения на потенциальное переполнение при арифметике. Для критических расчётов используйте Math.addExact(), Math.multiplyExact() — они выбрасывают ArithmeticException при переполнении.
Если требуется более 64 бит — используйте BigInteger. Это объектный тип, не примитив, но позволяет работать с произвольно большими целыми числами.



#Java #для_новичков #beginner #long