Solucionado (ver solução)
Solucionado
(ver solução)
4
respostas

Stack e Heap

Olá professor, boa noite, como a JVM aloca memória (Heap ou Stack) existe de fato alocação em áreas diferentes? Conseguimos exemplificar de forma prática isso, tipo, um algoritmo que mostra como acessar cada memória? No vídeo percebi que os objetos são criados na Heap, e o que é gerado na Stack?

4 respostas

Olá, José.

Como a JVM aloca memória (Heap ou Stack) existe de fato alocação em áreas diferentes?

Sim. Como você já citou, aloca em stack ou em heap.

Conseguimos exemplificar de forma prática isso, tipo, um algoritmo que mostra como acessar cada memória?

Hm. Não acho que seja possível com um código, mas existem ferramentas que mostram como está o desempenho da sua máquina virtual mostrando a saúde da memória com a quantidade de objetos criados/destruídos, etc.

No vídeo percebi que os objetos são criados na Heap, e o que é gerado na Stack?

Na stack são armazenados os valores de variáveis primitivas. valores estáticos e referências para objetos.

Para mais informações, tem um artigo bem legal na InfoQ: Uma breve introdução ao gerenciamento de memória em Java

Oi José,

Ótima pergunta! Existem sim duas áreas de memórias: uma para a pilha e outra para o heap. Todos os objetos são alocados no heap, então fica a pergunta: o que vai para a stack?

Uma coisa que vai para a pilha são as variáveis locais (os objetos não vão, mas as referências para eles vão). Então esse código

class StackTest {
    public static void main(String[] args) {
        Object o1=null,o2=null,...,o12199=null;
        }
}

quando rodado limitando-se o tamanho da pilha (-Xss160k diz para a JVM usar apenas 160KB para a pilha):

$ java -Xss160k StackTest                         
Exception in thread "main" java.lang.StackOverflowError
    at StackTest.main(StackTest.java:3)

Repare que não alocamos nada! Apenas a quantidade de referências (que ficam na pilha) é suficiente para estourar a memória. Algumas outras coisas também ficam na pilha, como as chamadas e os parâmetros dos métodos (e é por isso que recursão infinita causa estouro de pilha - stack overflow). Esse tópico é relativamente complicado, então não se preocupe em aprender detalhes no início :)

OBS: No código eu coloquei ... pois o código é grande demais para ser postado aqui no fórum. Se quiser testá-lo na sua casa, pode encontrá-lo em https://gist.github.com/gabrielrussoc/fe8b8d1f0339ad8baf7b81ae037c7b7a

Olá Arthur, muito bom o artigo, deu pra entender um pouco sobre a questão do uso da memória e como a JVM libera ela, tem como me informar alguma ferramenta que faz o acompanhamento da JVM e o desempenho de memória?

Gabriel, valeu o post, esclarecedor, de fato o algoritmo que vc me passou mostra um estouro na pilha, na verdade um ataque direto (Travou meu eclipse algumas vezes, desisti de tentar rodar, :-) !).

Concluindo: Posso dizer que stack é uma área onde se aloca conteúdo mais dinâmico (exemplo: variáveis locais), ou seja, conteúdo que não precisa de um ciclo de vida longo? E já no heap são conteúdos menos dinâmicos, tipo estruturas de classe?

Grato.

solução!

Olá, José.

Concluindo: Posso dizer que stack é uma área onde se aloca conteúdo mais dinâmico (exemplo: variáveis locais), ou seja, conteúdo que não precisa de um ciclo de vida longo? E já no heap são conteúdos menos dinâmicos, tipo estruturas de classe?

É o contrário. A stack é o conteúdo estático. Apesar de você poder mudar o valor de uma variável local/primitiva, você só está trocando os valores. Inclusive as estruturas de classe, elas ficam na stack assim como as variáveis de referência.

A heap que é dinâmica. Você consegue aumentar e diminuir o tamanho dela com configurações, é mantida pelo Garbage Collector e também tem várias heurísticas otimizadas só para as instâncias criadas à partir das especificações.