Есть ли какой-нибудь метод sizeof в Java?

Есть ли встроенный метод в Java, чтобы найти размер любого типа данных? Есть ли способ найти размер?

Ответ 1

Нет. В стандартной библиотеке классов Java SE такого метода нет.

Представление дизайнеров состоит в том, что он не нужен в Java, поскольку язык устраняет необходимость в приложении 1 чтобы знать, сколько места нужно зарезервировать для примитивного значения, объект или массив с заданным количеством элементов.

Вы могли бы подумать, что оператор sizeof был бы полезен для людей, которым необходимо знать, сколько места занимают их структуры данных. Однако вы также можете получить эту информацию и многое другое, просто и надежно с помощью профилировщика памяти Java, поэтому нет необходимости в методе sizeof.


@Davor указывает, что sizeof(someInt) будет более читаемым, чем 4. Я не уверен, что согласен... потому что я думаю, что каждый программист Java должен знать, что int всегда 32 бита (4 байта). (И кроме того, редко бывает необходимо использовать размер типа в Java-коде...)

Однако, если вы принимаете этот аргумент удобочитаемости, тогда средство находится в ваших руках. Просто определите класс, подобный этому...

public class PrimitiveSizes {
    public static int sizeof(byte b) { return 1; } 
    public static int sizeof(short s) { return 2; }
    // etcetera
}

... и статически импортировать его...

import static PrimitiveSizes.*;

Почему разработчики Java не реализовали это в стандартных библиотеках? Я предполагаю, что:

  • они не думают, что в этом есть необходимость,
  • они не думают, что для этого существует достаточный спрос, и
  • они не считают, что это стоит усилий.

Ключевое слово в приведенном выше выражении они. (Неважно, что вы или я об этом думаем... если у вас нет определенного влияния в процессе принятия решений.)

Также возникает вопрос, что следующее требование будет для метода sizeof(Object o), чреватого техническими трудностями.


1 - Программисту, возможно, потребуется знать, чтобы проектировать пространственно-эффективные структуры данных. Однако я не могу себе представить, почему эта информация потребуется в коде приложения во время выполнения через вызов метода.

Ответ 2

Из статьи в JavaWorld

Поверхностный ответ заключается в том, что Java не предоставляет ничего подобного C sizeof(). Однако, подумайте, почему иногда может понадобиться программист Java.

Программист C C управляет большинством распределений памяти базы данных, и sizeof() незаменим для того, чтобы знать размеры блоков памяти для выделить. Кроме того, C-распределители памяти, такие как malloc(), делают почти ничего, что касается инициализации объекта: программист должен установить все поля объектов, которые являются указателями на другие объекты. Но когда все сказано и закодировано, выделение памяти C/С++ вполне эффективным.

Для сравнения, привязка и построение объектов Java привязаны (невозможно использовать выделенные, но неинициализированные объект). Если класс Java определяет поля, которые являются ссылками к другим объектам, также принято устанавливать их при строительстве время. Поэтому выделение Java-объекта часто выделяет множество взаимосвязанные экземпляры объектов: граф объекта. В сочетании с автоматическая сборка мусора, все это слишком удобно и может вы чувствуете, что вам никогда не придется беспокоиться о распределении памяти Java подробности.

Конечно, это работает только для простых приложений Java. По сравнению с C/С++, эквивалентные Java-структуры данных, как правило, занимают больше физических Память. При разработке программного обеспечения предприятия, приближаясь к максимальная доступная виртуальная память на сегодняшний день 32-разрядные JVM - это общая ограничение масштабируемости. Таким образом, Java-программист мог извлечь выгоду из sizeof() или что-то подобное, чтобы следить за тем, структуры данных становятся слишком большими или содержат узкие места памяти. К счастью, отражение Java позволяет вам написать такой инструмент довольно легко.

Прежде чем продолжить, я обойдусь частыми, но неправильными ответы на этот вопрос. Ошибка: размер() не нужен потому что размеры базовых типов Java фиксированы.

Да, Java int - 32 бита во всех JVM и на всех платформах, но это является только требованием спецификации языка для программист-воспринимаемая ширина этого типа данных. Такой int является по существу, абстрактный тип данных и может быть подкреплен, скажем, 64-битное физическое запоминающее слово на 64-битной машине. То же самое касается Непримитивные типы: спецификация языка Java ничего не говорит о как поля классов должны быть выровнены в физической памяти или что массив логических значений не может быть реализовано как компактный битвектор внутри JVM. Ошибка: вы можете измерить размер объекта, сериализируя его в поток байтов и просмотр результирующей длины потока

Причина, по которой это не работает, заключается в том, что макет сериализации только удаленное отражение истинного макета в памяти. Один простой способ см. это, глядя на то, как строки становятся сериализованными: в памяти каждый char составляет не менее 2 байтов, но в сериализованной форме строками являются UTF-8 закодировано, и поэтому любой контент ASCII занимает вдвое меньше места

Ответ 3

Библиотека Java Native Access обычно используется для вызова собственных общих библиотек с Java. Внутри этой библиотеки существуют методы определения размера объектов Java:

Метод getNativeSize(Class cls), и его перегрузки будут обеспечивать размер для большинства классов.

В качестве альтернативы, если ваши классы наследуются от класса JNA Structure, будет доступен метод calculateSize(boolean force).

Ответ 4

Вы можете выполнять манипуляции с битами, как показано ниже, для получения размера примитивов:

public int sizeofInt() {
    int i = 1, j = 0;
    while (i != 0) {
        i = (i<<1); j++;
    }
    return j;
}

public int sizeofChar() {
    char i = 1, j = 0;
    while (i != 0) {
        i = (char) (i<<1); j++;
    }
    return j;
}

Ответ 5

Как упоминалось здесь, есть возможность получить размер примитивных типов через свои обертки.

например. для long это может быть Long.SIZE / Byte.SIZE из java 1.5 (как уже упоминалось zeodtr уже) или Long.BYTES как из java 8

Ответ 6

Вы можете использовать Integer.SIZE/8, Double.SIZE/8 и т.д. для примитивных типов из Java 1.5.

Ответ 7

Класс Instrumentation имеет метод getObjectSize(), однако вам не нужно использовать его во время выполнения. Самый простой способ изучить использование памяти - использовать профилировщик, который предназначен для отслеживания использования памяти.

Ответ 8

Я решил создать перечисление без соблюдения стандартных соглашений Java. Возможно, вам это нравится.

public enum sizeof {
    ;
    public static final int FLOAT = Float.SIZE / 8;
    public static final int INTEGER = Integer.SIZE / 8;
    public static final int DOUBLE = Double.SIZE / 8;
}

Ответ 11

Я не думаю, что это в API Java. но большинство типов данных, которые имеют в нем несколько элементов, имеют метод size(). Я думаю, вы можете легко написать функцию для проверки размера самостоятельно?

Ответ 13

В SourceForge.net есть класс /jar, который использует инструменты Java для вычисления размера любого объекта. Здесь ссылка на описание: java.sizeOf