CodeGym /Blogue Java /Random-PT /Explorando perguntas e respostas de uma entrevista de emp...
John Squirrels
Nível 41
San Francisco

Explorando perguntas e respostas de uma entrevista de emprego para um cargo de desenvolvedor Java. Parte 6

Publicado no grupo Random-PT
Olá Mundo! É essencial para qualquer desenvolvedor nunca parar de crescer. Afinal, se você parar, corre o risco de perder a demanda e sair totalmente do mercado de trabalho. O mundo da TI está em constante evolução e avanço – você precisa acompanhá-lo. Mas, ao mesmo tempo, você não pode simplesmente usar as tecnologias mais recentes para não esquecer os "clássicos" (tópicos clássicos de desenvolvimento de software). Hoje quero continuar minha discussão sobre “tópicos clássicos” para desenvolvedores Java. Explorando perguntas e respostas de uma entrevista de emprego para um cargo de desenvolvedor Java.  Parte 6 - 1Devo ressaltar que minhas respostas não são a palavra final. Elas são apenas minha opinião sobre as respostas corretas – você pode discordar de algumas delas. Tudo bem, então fique à vontade para compartilhar sua opinião nos comentários. Você pode encontrar links para as partes anteriores da revisão no final do artigo. Explorando perguntas e respostas de uma entrevista de emprego para um cargo de desenvolvedor Java.  Parte 6 - 2

Bibliotecas e padrões

52. O que é hibernar? Qual é a diferença entre JPA e Hibernate?

Para responder a esta pergunta, acho que primeiro precisamos entender o que é JPA. É uma especificação que descreve um mapeamento objeto-relacional de objetos Java simples e fornece uma API para armazenar, recuperar e manipular tais objetos. Ou seja, os bancos de dados relacionais (BDs) são representados como um conjunto de tabelas interconectadas. E JPA é um padrão amplamente adotado que descreve como os objetos podem interagir com bancos de dados relacionais. Como você pode ver, JPA é algo abstrato e intangível. É como a ideia em si, a abordagem. Explorando perguntas e respostas de uma entrevista de emprego para um cargo de desenvolvedor Java.  Parte 6 - 3Mas o Hibernate é uma biblioteca específica que implementa paradigmas JPA. Ou seja, você pode utilizar esta biblioteca para trabalhar com um banco de dados relacional através de objetos que representam dados no banco de dados (Entidade). Diz-se que esta biblioteca está muito próxima dos ideais JPA. Talvez seja por isso que se tornou popular. Como você pode imaginar, sua popularidade justificou maiores desenvolvimentos e melhorias. Além disso, o uso generalizado decorre de uma vasta comunidade que já explorou todas as questões possíveis e impossíveis relacionadas a esta ferramenta. O Hibernate foi exaustivamente estudado e, como se vê, é confiável. Há uma boa razão pela qual até mesmo a implementação JPA ideal no Spring geralmente usa o Hibernate nos bastidores.

53. O que é cascata? Como é usado no Hibernate?

Como eu disse anteriormente, a comunicação no Hibernate acontece através de objetos de dados chamados entidades. Essas entidades representam tabelas específicas no banco de dados e, como você deve se lembrar, as classes Java podem conter referências a outras classes. Esses relacionamentos também são refletidos no banco de dados. Via de regra, elas são chaves estrangeiras (para relacionamentos OneToOne, OneToMany, ManyToOne) ou tabelas intermediárias (para relacionamentos ManyToMany). Quando sua entidade possui referências a outras entidades relacionadas, anotações são colocadas acima dessas referências para indicar o tipo de relacionamento: @OneToOne, @OneToMany, @ManyToOne, @ManyToMany. Você pode especificar o tipo de cascata para esse relacionamento na propriedade cascata das anotações. JPA possui métodos específicos para interação com entidades (persistir, salvar, mesclar...). Os tipos cascata são usados ​​para mostrar como os dados relacionados devem se comportar; esses métodos são usados ​​em uma entidade de destino. Então, quais são as estratégias em cascata (tipos de cascata)? O padrão JPA prevê o uso de seis tipos de cascata:
  • PERSIST — as operações de salvamento ocorrem em cascata (para os métodos save() e persist() ). Em outras palavras, se salvarmos uma entidade que está associada a outras entidades, então essas entidades também serão salvas no banco de dados (se ainda não estiverem lá).

  • MERGE — as operações de atualização ocorrem em cascata (para o método merge() )

  • REMOVE — as operações de exclusão ocorrem em cascata ( método remove() )

  • ALL — contém três operações em cascata ao mesmo tempo — PERSISTMERGEREMOVE

JPA tem o conceito de entidade persistente - uma entidade associada aos seus dados no banco de dados e controlada pela sessão (conexão) atual. Se você alterá-lo sem salvar as alterações no banco de dados, os dados da entidade no banco de dados ainda serão alterados.
  • DETACH — entidades relacionadas não são gerenciadas pela sessão ( método detach() ). Ou seja, quando os dados das entidades relacionadas são alterados, os dados do banco de dados não são atualizados automaticamente — eles são convertidos de persistentes para desanexados (ou seja, a entidade não é gerenciada pelo JPA)

  • REFRESH — toda vez que uma entidade é atualizada com dados do banco de dados ( refresh() — atualiza objetos desanexados), suas entidades relacionadas também são atualizadas. Por exemplo, você alterou de alguma forma os dados retirados do banco de dados e deseja restaurar os valores originais. Nesse caso, você achará esta operação útil.

Explorando perguntas e respostas de uma entrevista de emprego para um cargo de desenvolvedor Java.  Parte 6 - 4O Hibernate suporta todas essas operações em cascata padrão e também introduz três delas próprias:
  • REPLICATE — usado quando temos mais de uma fonte de dados e queremos que os dados sejam sincronizados (método de replicação do Hibernate). Todas as entidades devem ter identificadores (id) para garantir que possam ser criadas sem problemas (para garantir que a mesma entidade não tenha ids diferentes para bases de dados diferentes)

  • SAVE_UPDATE — salvar/excluir em cascata (para o método saveOrUpdate do Hibernate)

  • LOCK — o oposto da operação DETACHED : converte uma entidade desanexada de volta ao estado persistente, ou seja, a sessão atual rastreará a entidade mais uma vez

Se nenhum tipo de cascata for selecionado, uma operação na entidade não afetará outras entidades associadas a ela.

54. Uma classe Entity pode ser abstrata?

De acordo com 2.1 A classe de entidade da especificação JPA , " Tanto as classes abstratas quanto as concretas podem ser entidades. " Portanto, a resposta é sim, uma classe abstrata pode ser uma entidade e pode ser marcada com a anotação @Entity.

55. O que é um gestor de entidade? Pelo que é responsável?

Em primeiro lugar, gostaria de salientar que o EntityManager é um componente crucial do JPA . É utilizado para interação das entidades com o banco de dados. Em geral, os métodos de interação da entidade com o banco de dados são chamados na entidade (persistir, mesclar, remover, desanexar)... Mas também observo que esse componente geralmente não é um singleton para todo o aplicativo. Geralmente é leve, um é excluído e um novo é criado usando EntityManagerFactory . Se traçarmos um paralelo com JDBC , onde EntityManagerFactory é análogo a DataSource , então EntityManager é análogo a Connection . Anteriormente, mencionei que uma entidade persistente é uma entidade gerenciada pela conexão atual. Esta entidade é gerenciada pelo EntityManager , que está intimamente relacionado à conexão atual, e pelo TransactionManager , que é responsável por abrir/fechar transações. Na figura abaixo você pode ver o ciclo de vida da entidade: Explorando perguntas e respostas de uma entrevista de emprego para um cargo de desenvolvedor Java.  Parte 6 - 5O EntityManager gerencia a entidade quando ela está no estágio Gerenciado (quando é persistente, pois possui conexão com o EntityManager ). Ou seja, não é novo e também não foi removido. Quando uma entidade é nova ou removida, podemos dizer que ela também está desanexada, pois o EntityManager não a gerencia. Existem diferentes estratégias para o EntityManager . Você pode ter um singleton do EntityManager para todo o aplicativo ou criar um novo para cada conexão. Se você estiver usando o Spring, a criação/exclusão do EntityManager será gerenciada automaticamente nos bastidores (mas isso não significa que você não possa personalizá-lo por si mesmo ^^). Preciso mencionar que um ou mais EntityManagers formam um contexto de persistência . Um contexto de persistência é um ambiente no qual instâncias de entidades são sincronizadas com entidades semelhantes no banco de dados (como eu disse, isso só funciona para entidades persistentes). Se você se aprofundar no JPA (que eu recomendo fortemente), encontrará esse conceito com muita frequência.

56. O que é a classe Assert? Por que é usado?

Não ouvi falar de tal classe em JPA , então assumirei que esta pergunta se refere a uma classe encontrada na biblioteca JUnit usada para testes de unidade. Nesta biblioteca, a classe Assert é usada para verificar os resultados da execução do código (aqui assert significa uma afirmação de que você possui estados/dados específicos em um local específico no código). Por exemplo, digamos que você esteja testando um método que supostamente cria um gato. Você executa o método e obtém algum resultado:
Cat resultOfTest = createCat();
Mas você precisa ter certeza de que foi criado corretamente, certo? Então você cria manualmente um gato específico ( esperadoCat ) com exatamente os parâmetros que você espera ver no gato obtido do método createCat() . Então você usa a classe Assert para verificar os resultados:
Assert.assertEquals(resultOfTest, expectedCat);
Se os gatos forem diferentes, será lançado um AssertionError , que nos informa que não obtivemos os resultados esperados. A classe Assert possui muitos métodos diferentes que cobrem uma variedade de operações úteis na verificação dos resultados esperados. Aqui estão alguns deles:
  • assertTrue(<boolean>) — espera-se que o valor passado como argumento seja verdadeiro

  • assertFalse(<boolean>) — espera-se que o valor passado como argumento seja falso

  • assertNotEquals(<object1>, <object2>) — os objetos passados ​​como argumentos devem ser diferentes quando comparados usando iguais ( false )

  • assertThrows(<ClassNameOfException>.class, <exceptionObject>) — espera-se que o segundo argumento seja uma exceção lançada pelo primeiro argumento (ou seja, o segundo argumento é geralmente uma chamada de método que deve lançar uma exceção do tipo requerido)

Corda

57. Descreva a classe String do Java

String é uma classe Java padrão responsável por armazenar e manipular valores de string (sequências de caracteres). É uma classe imutável (escrevi sobre imutável anteriormente aqui ), ou seja, os dados dos objetos desta classe não podem ser alterados após serem criados. Gostaria de observar imediatamente que as classes StringBuilder e StringBuffer são essencialmente idênticas — a única diferença é que uma delas se destina ao uso em um ambiente multithread ( StringBuffer ). Essas classes são como String , mas diferem por serem mutáveis ​​. Mesmo depois de criados, eles permitem modificar as strings que representam, sem criar um novo objeto. Seus métodos diferem dos métodos String padrão e são projetados para manipulação de strings (há uma razão pela qual eles o chamam de construtor).

58. Quais são as formas de criar um objeto String? Onde ele é criado?

A maneira mais comum de criar uma string é simplesmente especificar o valor que queremos entre aspas duplas:
String str = "Hello World!";
Você também pode fazer isso explicitamente usando new :
String str = new String("Hello World!");
Você também pode criar uma string a partir de um array de caracteres:
char[] charArr = {'H','e','l','l','o',' ', 'W','o','r','l','d','!'};
String str = new String(charArr);
Podemos fazer isso chamando o método toString em algum objeto:
String str = someObject.toString();
Podemos fazer isso chamando qualquer outro método que retorne uma string. Exemplo:
BufferedReader reader = new BufferedReader(new InputStreamReader(System.in));
String str = reader.readLine();
Você entende que pode haver muitas maneiras de criar uma string. Quando um objeto String é criado, ele é armazenado em um pool de strings , que discutiremos com mais detalhes em uma das questões abaixo.

59. Como você compara duas strings Java e como você as classifica?

Java usa um sinal de igual duplo ( == ) para realizar comparações. Se precisarmos comparar valores simples como ints, nós os usaremos. Mas este método não é adequado para comparar objetos completos. Ele irá apenas comparar referências, ou seja, se as referências apontam para o mesmo objeto ou não. Isso significa que se compararmos dois objetos com os mesmos valores de campo usando == , obteremos false . Os campos têm os mesmos valores, mas os próprios objetos ocupam locais diferentes na memória. Objetos string , apesar de sua simplicidade enganosa, ainda são objetos. Compará-los usando == também não é apropriado (apesar da presença de um conjunto de strings). A solução adequada é o método equals padrão da classe Object , que precisa ser substituído para funcionar corretamente (por padrão, ele usa == para comparações). A classe String a substitui, então apenas usamos sua implementação:
String firstStr = "Hello World!";
String secondStr = "Hello World!";
boolean isEquals = firstStr.equals(secondStr);
Explorando perguntas e respostas de uma entrevista de emprego para um cargo de desenvolvedor Java.  Parte 6 - 6Já falamos sobre comparações para igualdade. Agora vamos descobrir comparações para classificação. Afinal, se vamos classificar algo, precisamos saber qual princípio usaremos para classificar. Para fazer isso, você pode usar TreeSet , um conjunto classificado padrão. Esta estrutura de dados depende do algoritmo de árvore vermelho-preto e classifica o conjunto de acordo com um princípio de classificação especificado. Como eu disse anteriormente, você precisa entender como classificar objetos de um determinado tipo. Para atribuir o método de comparação para classificação, use comparators . Normalmente você precisa implementá-los para as classes que deseja classificar, mas no caso de String , eles já estão implementados. Da mesma forma, simplesmente adicionamos nossas strings ao TreeSet e ele as classificará para nós:
TreeSet<String> sortedSet = new TreeSet<>();
sortedSet.add("B");
sortedSet.add("C");
sortedSet.add("A");
sortedSet.forEach(System.out::println);
Saída do console:
abc

60. Forneça um algoritmo para converter uma string em caracteres. Escreva o código correspondente

Como eu disse anteriormente, os objetos String têm vários métodos úteis diferentes. Um deles é toCharArray . Este método converte uma string em uma matriz de caracteres:
String str = "Hello world";
char[] charArr = str.toCharArray();
A seguir, temos um array de caracteres que podemos referenciar por índice:
char firstChar = charArr[0]; // H

61. Como você converte uma string em uma matriz de bytes e vice-versa? Escreva o código correspondente

A classe String possui um método getBytes , que é semelhante ao método toCharArray e retorna a string como uma matriz de bytes:
String str = "Hello world";
byte[] byteArr = str.getBytes();
byte firstChar = byteArr[6]; // 119
Chegamos à conclusão lógica de nossa análise de hoje. Obrigado por ler!
Comentários
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION