Por que a sobrecarga ao alocar objetos / matrizes em Java?

9

Quantos bytes uma matriz ocupa em Java? Suponha que seja uma máquina de 64 bits e também assuma que há N elementos em uma matriz, portanto todos esses elementos ocupariam 2 * N, 4 * N ou 8 * N bytes para diferentes tipos de matriz.

E uma palestra em Coursera diz que ocuparia 2 * N + 24, 4 * N + 24 ou 8 * N + 24 bytes para uma matriz de elementos N e os 24 bytes são chamados de sobrecarga, mas não explicaram por que a sobrecarga é necessário.

Os objetos também têm sobrecargas, que são 16 bytes.

O que exatamente são essas despesas gerais? De que são compostos esses 24/16 bytes?

Além disso, essas despesas gerais existem apenas em Java? Que tal C, C ++ e Python?

Gnijuohz
fonte
11
@Gnijuohz: Você quer perguntar: de quais dados essa sobrecarga é composta?
FrustratedWithFormsDesigner
@YannisRizos: Acho que o OP quer saber o que realmente está nesses 24 bytes, para matrizes.
FrustratedWithFormsDesigner
@FrustratedWithFormsDesigner Ah, essa parece ser uma melhor interpretação da pergunta do que a minha.
yannis
@YannisRizos desculpe pela minha má atitude. Mas quando você publica esse link, não posso deixar de pensar que isso é algum tipo de sarcasmo. Muito defensivo, eu acho.
Gnijuohz 28/08/2012

Respostas:

16

Cada objeto Java possui um cabeçalho que contém informações importantes para a JVM. O mais importante é uma referência à classe do objeto (uma palavra de máquina), e existem alguns sinalizadores usados ​​pelo coletor de lixo e para gerenciar a sincronização (uma vez que todos os objetos podem ser sincronizados) que ocupam outra palavra de máquina (usar palavras parciais prejudicar o desempenho). Então, são 2 palavras, que são 8 bytes em sistemas de 32 bits e 16 bytes em 64 bits. Além disso, as matrizes precisam de um campo int para o comprimento da matriz, que possui outros 4 bytes, possivelmente 8 em sistemas de 64 bits.

Quanto aos outros idiomas:

  • C não possui objetos, portanto, é claro que não possui cabeçalhos, mas pode ter um cabeçalho em cada pedaço de memória alocado separadamente.

  • No C ++, você não possui coleta de lixo e não pode usar objetos arbitrários para sincronização, mas se você tiver classes com métodos substituídos, cada objeto terá um ponteiro para sua vtable, assim como a referência do objeto Java à sua classe. Se você usar ponteiros inteligentes que fazem coleta de lixo, eles precisarão de dados de limpeza.

  • Não conheço o Python, mas tenho certeza de que ele também precisa de uma referência para a classe e informações de limpeza para o coletor de lixo.

Michael Borgwardt
fonte
Há trabalho a acontecer no OpenJDK no momento para reduzir o tamanho dos cabeçalhos objeto, pequenos, mas importantes passos :-)
Martijn Verburg
No C ++, apenas as classes polimórficas precisam de vtables. std::pair<int, float>é uma classe simples que não precisa de uma vtable. Como resultado, pode muito bem caber em 8 bytes. Além disso, ponteiros inteligentes não precisam adicionar tarefas domésticas. Um contra-exemplo claro é std::unique_ptr<T>, que normalmente é tão grande quanto o bruto T*(unique_ptr, é claro, não faz GC).
precisa saber é o seguinte
4
C também possui uma sobrecarga, cada mallocbloco de memória alocado precisa de um cabeçalho que freeentão seja usado.
Herby
Pelo menos uma biblioteca malloc que eu conheço usa um cabeçalho de 8 bytes em sistemas de 32 bits (que é um comprimento de 4 bytes entre colchetes por dois conjuntos de valores sentinela de 2 bytes, IIRC).
Donal Fellows