JavaRush /Blogue Java /Random-PT /Ciclo de vida do objeto

Ciclo de vida do objeto

Publicado no grupo Random-PT
Olá! Acho que você não ficará muito surpreso se dissermos que o tamanho da memória do seu computador é limitado :) Até mesmo um disco rígido, que é muitas vezes maior que a RAM, pode ser preenchido com seus jogos favoritos, séries de TV, e assim por diante. Para evitar que isso aconteça, você precisa monitorar o estado atual da memória e excluir arquivos desnecessários do seu computador. O que a programação Java tem a ver com tudo isso? Direto! Afinal, quando qualquer objeto é criado pela máquina Java, é alocada memória para ele. Em um programa realmente grande, dezenas e centenas de milhares de objetos são criados, cada um com sua própria memória alocada. Ciclo de vida do objeto - 1Mas há quanto tempo você acha que todos esses objetos existem? Eles “vivem” durante todo o tempo em que nosso programa está em execução? Claro que não. Com todas as vantagens dos objetos Java, eles não são imortais :) Os objetos têm seu próprio ciclo de vida. Hoje faremos uma pequena pausa na escrita de código e veremos esse processo :) Além disso, é muito importante para entender o funcionamento do programa e gerenciar recursos. Então, onde começa a vida de um objeto? Como uma pessoa - desde o seu nascimento, isto é, a criação.
Cat cat = new Cat();//вот сейчас и начался vital цикл нашего an object Cat!
Primeiro, a Java Virtual Machine aloca a quantidade necessária de memória para criar o objeto. Então ela cria um link para ele, no nosso caso - catpara poder rastreá-lo. Depois disso, todas as variáveis ​​são inicializadas, o construtor é chamado e eis que nosso novo objeto já está vivendo sua própria vida :) A vida útil dos objetos é diferente, não há números exatos aqui. Em qualquer caso, durante algum tempo ele vive dentro do programa e desempenha suas funções. Para ser mais preciso, um objeto está “vivo” enquanto houver referências a ele. Assim que não houver mais links, o objeto “morre”. Por exemplo:
public class Car {

   String model;

   public Car(String model) {
       this.model = model;
   }

   public static void main(String[] args) {
       Car lamborghini  = new Car("Lamborghini Diablo");
       lamborghini = null;

   }

}
No método, main()o objeto carro Lamborghini Diablo deixa de estar vivo já na segunda linha. Havia apenas um link para ele e agora esse link foi atribuído null. Como não há mais referências ao Lamborghini Diablo, ele vira “lixo”. Não é necessário redefinir o link:
public class Car {

   String model;

   public Car(String model) {
       this.model = model;
   }

   public static void main(String[] args) {
       Car lamborghini  = new Car("Lamborghini Diablo");

       Car lamborghiniGallardo = new Car("Lamborghini Gallardo");
       lamborghini = lamborghiniGallardo;
   }

}
Aqui criamos um segundo objeto, após o qual pegamos a referência lamborghinie a atribuímos a este novo objeto. Existem agora Lamborghini Gallardoduas referências ao objeto, mas Lamborghini Diablonenhuma ao objeto. Portanto o objeto Diablose torna lixo. E neste momento, o mecanismo Java embutido chamado coletor de lixo, ou em outras palavras - Garbage Collector, GC, entra em operação.
Ciclo de vida do objeto - 2
O coletor de lixo é um mecanismo interno do Java responsável por liberar memória, ou seja, remover dela objetos desnecessários. Não foi à toa que escolhemos uma imagem com um aspirador robô para retratá-lo. Afinal, o coletor de lixo funciona quase da mesma maneira: em segundo plano, ele “viaja” pelo seu programa, coleta o lixo e ao mesmo tempo você praticamente não interage com ele. Sua função é remover objetos que não são mais utilizados no programa. Assim, libera memória do computador para outros objetos. Você se lembra que no início da palestra falamos que na vida cotidiana é preciso monitorar o estado do seu computador e deletar arquivos antigos? Portanto, no caso de objetos Java, o coletor de lixo faz isso para você. O Garbage Collector é iniciado várias vezes durante a operação do seu programa: ele não precisa ser chamado especificamente e receber comandos, embora isso seja tecnicamente possível. Posteriormente falaremos mais sobre ele e analisaremos mais detalhadamente o processo de seu trabalho. No momento em que o coletor de lixo chega ao objeto, pouco antes de sua destruição, um método especial é chamado no objeto - finalize(). Pode ser usado para liberar alguns recursos adicionais que o objeto estava usando. O método finalize()pertence à classe Object. Ou seja, junto com equals(), hashCode()e toString(), que você já conheceu anteriormente, qualquer objeto o possui. Sua diferença em relação a outros métodos é que ele é... como dizer... muito caprichoso. Ou seja, nem sempre é chamado antes de destruir um objeto. Programar é uma coisa precisa. O programador diz ao computador para fazer alguma coisa, e o computador faz. Você provavelmente já está acostumado com esse comportamento e pode ser difícil aceitar a ideia no início: “Antes que os objetos sejam destruídos, o método da finalize()classe é chamado Object. Ou não é chamado. Se tivermos sorte!" No entanto, isso é verdade. A própria máquina Java determina se deve chamar o método finalize()em cada caso específico ou não. Por exemplo, vamos tentar executar o seguinte código para fins de experiência:
public class Cat {

   private String name;

   public Cat(String name) {
       this.name = name;
   }

   public Cat() {
   }

   public static void main(String[] args) throws Throwable {

       for (int i = 0 ; i < 1000000; i++) {

           Cat cat = new Cat();
           cat = null;//вот здесь первый an object становится доступен сборщику мусора
       }
   }

   @Override
   protected void finalize() throws Throwable {
       System.out.println("Объект Cat уничтожен!");
   }
}
Criamos um objeto Cate na próxima linha de código redefinimos a única referência a ele. E assim - um milhão de vezes. Substituímos explicitamente o método finalize()e ele deve imprimir a string no console um milhão de vezes, sempre antes de destruir o objeto Cat. Mas não! Para ser mais preciso, ele funcionou apenas 37.346 vezes no meu computador! Ou seja, apenas em 1 dos 27 casos a máquina Java que instalei decidiu chamar um método finalize()- em outros casos, a coleta de lixo prosseguiu sem isso. Tente executar este código você mesmo: provavelmente o resultado será diferente. Como você pode ver, finalize()é difícil chamá-lo de parceiro confiável :) Portanto, um pequeno conselho para o futuro: você não deve confiar no método finalize()no caso de liberar alguns recursos críticos. Talvez a JVM ligue, talvez não. Quem sabe? Se durante seu tempo de vida seu objeto ocupou alguns recursos que foram super importantes para performance, por exemplo, manteve uma conexão aberta com o banco de dados, é melhor criar um método especial em sua classe para liberá-los e chamá-lo explicitamente quando o objeto for não é mais necessário. Desta forma você terá certeza de que o desempenho do seu programa não será prejudicado. No início dissemos que o gerenciamento de memória e a remoção de lixo são muito importantes, e isso é verdade. O manuseio inadequado de recursos e a falta de compreensão do processo de montagem de objetos desnecessários podem levar a vazamentos de memória. Este é um dos erros de programação mais famosos. O código escrito incorretamente pelo programador pode resultar na alocação de nova memória a cada vez para objetos recém-criados, enquanto objetos antigos e desnecessários não ficam disponíveis para remoção pelo coletor de lixo. Já que fizemos uma analogia com um aspirador robô, imagine o que aconteceria se, antes de ligar o robô, você espalhasse meias pela casa, quebrasse um vaso de vidro e deixasse um conjunto de Lego desmontado no chão. O robô, é claro, tentará fazer alguma coisa, mas em determinado momento ficará preso.
Ciclo de vida do objeto - 3
Para que funcione bem, é preciso manter o piso em bom estado e retirar de lá tudo que o aspirador não aguenta. O coletor de lixo funciona com o mesmo princípio. Se sobrarem muitos objetos no programa que ele não consegue coletar (como uma meia ou Lego para um aspirador de pó robô), a certa altura a memória acabará. E não apenas o programa que você escreveu irá congelar, mas também todos os outros programas em execução no computador naquele momento. Também não haverá memória suficiente para eles. É assim que se parecem o ciclo de vida do objeto e o coletor de lixo em Java. Não há necessidade de memorizar isso: basta entender o princípio de funcionamento. Na próxima palestra falaremos mais detalhadamente sobre esses processos, mas por enquanto você pode voltar a resolver problemas do JavaRush :) Boa sorte!
Comentários
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION