Каковы издержки памяти для метода Java?
Что такое служебные данные памяти для функции в классе?
Например,
Class A
{
int a
}
Class B
{
int a
int foo(int);
}
Таким образом, 100 экземпляров класса A должны быть 80 байтов. Примерно 100 экземпляров класса B?
Ответы
Ответ 1
Накладные расходы - это... нет.
Определение метода и адрес кода хранятся в объекте Class, который имеет уникальный экземпляр, к которому относится каждый экземпляр вашего объекта.
Так как это будет так, независимо от того, добавили ли вы этот метод, накладные расходы для каждого отдельного объекта ничего.
Ответ 2
80 байт, поскольку метод не включен в объект. Если вы не говорите также о типах "vtable", в этом случае, вероятно, 160 байт.
Разъяснение на 160 байт. 160 будет, если каждый объект выделил свою собственную таблицу vtable (что является одной возможной реализацией). В качестве альтернативы (и как указано в комментариях) лучшим способом будет один vtable для каждого класса, что будет означать 80 + размер указателя на vtable (вероятно, 4 или 8 байтов в зависимости от VM). Таким образом, 84 или 88 байт.
Все это полностью зависит от того, как VM выделяет память и занимается неконфиденциальными методами. Не зная, как реализована конкретная виртуальная машина, ни один из вопросов не может быть правильно ответил.
Ответ 3
Как было сказано несколькими другими людьми, метод не сохраняется в сериализации.
Вы можете легко выполнить тест, чтобы показать это в этом примере со следующим кодом.
import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectOutputStream;
import java.io.Serializable;
public class SerializationTest {
public static void main(String[] args) {
serialize(true);
serialize(false);
}
public static void serialize(boolean aOrB) {
FileOutputStream fos = null;
ObjectOutputStream out = null;
try {
fos = new FileOutputStream("output.txt");
out = new ObjectOutputStream(fos);
out.writeObject(aOrB ? new A() : new B());
out.close();
fos.close();
} catch (IOException ex) {
ex.printStackTrace();
}
File file = new File("output.txt");
System.out.println(file.length());
}
public static class A implements Serializable {
int a = 0;
}
public static class B implements Serializable {
int a = 0;
public int foo(int a) {
return a;
}
}
}
Для меня это печатает
48
48
Ответ 4
Объекты обоих классов будут использовать около 20-24 байта для 32/64-разрядных JVM.
Ответ 5
Метод не сохраняется в сериализованной форме. Это так просто.
Изменить: Что касается объектов в виртуальной машине во время выполнения, размер должен быть постоянным, независимо от того, сколько методов имеет класс объекта.
Ответ 6
Равно, 80! (короче говоря)
Ответ 7
Вероятно, размер указателя v-таблицы округлен до кратного 16.