Análise de código-fonte Java e perguntas da entrevista - perguntas da fila de entrevistas no código-fonte

Esta série de blog relacionado, Mu coluna referência de classe Java de código fonte e do sistema fabricantes entrevistador sucintamente Zhenti
abaixo desta coluna é o endereço GitHub:
Fonte resolvido: https://github.com/luanqiu/java8
artigo Demonstração: HTTPS: // GitHub.
colegas de classe com / luanqiu / java8_demo podem ver se necessário)

Análise de código-fonte Java e perguntas da entrevista - perguntas da fila de entrevistas no código-fonte

Frase introdutória
filas enfrentar questões em termos do código-fonte, a entrada geral do entrevistador vai bloquear o pool de threads, etc. Por uma questão de conhecimento, de forma lenta e pediu para fila, porque o bloqueio, o pool de threads que não aprendemos, por isso fui direto para o tema deste capítulo Vamos começar com a fila e ver quais perguntas da entrevista estão na fila (existem muitos tipos de fila. Neste artigo, ao falar sobre as características gerais da fila, eles estão falando sobre as características gerais da maioria das filas. Instruções).

1 Perguntas da entrevista

1.1 Fale sobre sua compreensão das filas, a diferença entre filas e coleções.
Resposta : Compreensão da fila:

  1. Primeiro, a fila em si é um contêiner e a camada inferior também terá estruturas de dados diferentes.Por exemplo, LinkedBlockingQueue é uma estrutura de lista vinculada na parte inferior, para que possa manter a ordem do primeiro a entrar, por exemplo. A ordem de primeiro a entrar, primeiro a sair, etc., a estrutura de dados subjacente é diferente, o que também causa uma implementação de operação diferente;
  2. Algumas filas (como LinkedBlockingQueue) fornecem uma função de armazenamento temporário, podemos colocar dados na fila e também podemos obter dados da fila, ambos podem ser feitos ao mesmo tempo;
  3. A fila desacopla a parte que produz dados da parte que consome dados. O produtor controla apenas a produção e o consumidor consome. Não há conexão necessária entre os dois. A fila é como um canal de dados entre o produtor e o consumidor, como LinkedBlockingQueue ;
  4. A fila também pode gerenciar consumidores e produtores.Por exemplo, quando a fila está cheia e alguns produtores ainda estão entregando dados, a fila pode bloquear o produtor e impedir que ela seja entregue.Por exemplo, quando a fila está vazia, há consumo Quando a pessoa chega para obter os dados, a fila pode deixar o consumidor morar e, quando houver, acordar o consumidor e permitir que o consumidor retorne os dados, como ArrayBlockingQueue;
  5. A fila também fornece uma função de bloqueio.Por exemplo, quando obtemos dados da fila, mas não há dados na fila, o encadeamento será bloqueado até que a fila tenha dados disponíveis para retornar.

A diferença entre fila e coleção:

  1. Semelhante a coleções, filas (algumas exceções) e coleções fornecem funções de armazenamento de dados.A estrutura de dados de armazenamento subjacente é um pouco semelhante.Por exemplo, LinkedBlockingQueue e LinkedHashMap usam listas vinculadas e ArrayBlockingQueue e ArrayList as usam. É uma matriz.
  2. A diferença com a coleção:
    • A estrutura de armazenamento subjacente de algumas filas e algumas coleções é muito semelhante, mas para realizar coisas diferentes, as APIs fornecidas pelos dois e suas operações subjacentes são diferentes.

    • A fila fornece uma função de bloqueio, que permite o gerenciamento simples de consumidores e produtores. Quando a fila estiver vazia, ele bloqueará o consumidor. Após outros threads executarem a operação de colocação, o consumidor bloqueado será despertado para permitir que o consumidor consuma os dados. Também quando a fila está cheia.

    • Desacoplando o produtor e o consumidor, a fila é como um pipeline entre o produtor e o consumidor, que apenas o joga e o consumidor consome continuamente, e os dois não se importam.

1.2 Quais filas têm a função de bloquear e como são bloqueadas?
Resposta : A fila fornece principalmente duas funções de bloqueio, como a seguir:

  1. LinkedBlockingQueue e ArrayBlockingQueue são dois tipos de filas de bloqueio. A capacidade do primeiro é o valor máximo de Inteiro e o tamanho do último array é fixo. As duas filas de bloqueio podem especificar a capacidade. Quando a fila estiver cheia, se houver dados de colocação de thread, o thread será Bloqueado, até que outros encadeamentos consumam dados, o encadeamento bloqueado será ativado e continuará sendo colocado.Quando a fila estiver vazia, se houver um encadeamento para coletar dados, o encadeamento será bloqueado até que a fila não esteja vazia e continue a levar.
  2. SynchronousQueue Fila síncrona, quando o thread é colocado, o thread correspondente deve consumir os dados, o thread put pode retornar, quando o thread leva, o thread correspondente precisa colocar dados, o take pode retornar, caso contrário, o bloqueio, por exemplo, thread A colocar dados A1 na fila.No momento, não há consumidor.O thread A não pode retornar e irá bloquear.O thread A não pode retornar até que um thread consuma dados A1.

1.3 Como a camada subjacente bloqueia?
Resposta : A fila em si não implementa a função de bloqueio, mas usa o mecanismo de espera e ativação da condição.A implementação subjacente do bloqueio é alterar o estado do encadeamento para suspensão, como falaremos na seção de bloqueio.

1.4 Qual é a diferença entre LinkedBlockingQueue e ArrayBlockingQueue?
Resposta : O mesmo ponto:
o mecanismo de bloqueio dos dois é aproximadamente o mesmo, por exemplo, quando a fila está cheia e vazia, o encadeamento será bloqueado.

Diferenças:

  1. A camada inferior de LinkedBlockingQueue é uma estrutura de lista vinculada, e a capacidade é o valor máximo de Interge por padrão.A camada inferior de ArrayBlockingQueue é uma matriz, e a capacidade deve ser especificada durante a inicialização.
  2. A estrutura subjacente dos dois é diferente; portanto, a implementação subjacente de pegar, colocar e remover também é diferente.

1.5 É seguro colocar dados na fila? Porque
R : É seguro para threads. Antes da colocação, a fila será bloqueada automaticamente. Após a conclusão da colocação, a trava será liberada automaticamente, garantindo que apenas um thread possa operar nos dados da fila ao mesmo tempo. Tome o LinkedBlockingQueue como exemplo. Adicionar bloqueio de colocação e operar apenas na cauda da equipe. Quando receber, ele adicionará um bloqueio de recepção e somente operará na cabeça da equipe. Ao remover, ele adicionará bloqueios de colocar e receber, portanto, várias operações são seguras para threads. , Podemos usá-lo com confiança em nosso trabalho.

1.6 Será bloqueado quando tirar? Como o put e o take estão bloqueados, apenas um dos métodos pode ser executado ao mesmo tempo.
Resposta :

  1. Sim, ele também será bloqueado durante a tomada.Por exemplo, quando o LinkedBlockingQueue executa o método take, ele exclui os dados atuais enquanto toma os dados, o que altera a estrutura de dados da lista vinculada, portanto, precisa ser bloqueado para garantir a segurança do encadeamento.
  2. Isso depende da situação.Para LinkedBlockingQueue, a entrada e a saída da fila serão bloqueadas, mas os bloqueios dos dois são diferentes, portanto, os dois não se afetam e podem ser executados ao mesmo tempo.Para ArrayBlockingQueue, put e take é o mesmo bloqueio, portanto, apenas um método pode ser executado por vez.

1.7 Quais são os riscos de usar os métodos de colocar e receber da fila frequentemente no trabalho e como evitá-los.
Resposta : Quando a fila estiver cheia, o uso do método put será bloqueado até que a fila não esteja cheia.
Quando a fila está vazia, o uso do método take será bloqueado até que a fila tenha dados.

Ambos os métodos são infinitos (para sempre, sem tempo limite), é fácil bloquear todos os segmentos.Quando o fluxo é grande, a máquina não possui segmentos disponíveis, por isso é recomendável usar os métodos de oferta e pesquisa quando o fluxo é grande Em vez dos dois, precisamos definir apenas o tempo de bloqueio do tempo limite.Se os dois métodos não obtiverem dados fora do tempo limite, eles retornarão ao valor padrão (LinkedBlockingQueue como exemplo), para que não cause tráfego intenso Threads estão bloqueados.

Essa também é uma das razões pelas quais os acidentes de produção ocorrem com frequência. A tentativa de usar os métodos de colocar e receber não pode ser encontrada no autoteste em horários normais. Os alunos que não estão familiarizados com o código-fonte não percebem que haverá problemas. , É provável que falhe, portanto, geralmente precisamos ser cautelosos ao usar filas em nosso trabalho.

1.8 Depois de colocar os dados na fila, existe uma maneira de deixar a fila executar depois de um tempo?
Resposta : Sim, o DelayQueue fornece esse mecanismo, que pode ser configurado para ser executado após um certo período de tempo. A única desvantagem dessa fila é que os dados são armazenados na memória. Ao reiniciar e desligar, é fácil perder os dados, por isso é agendado. Não definiremos o tempo por muito tempo, geralmente em alguns segundos.Se o horário agendado precisar ser definido por um longo tempo, considere adotar 延迟队列中间件(esse tipo de middleware persistirá nos dados, sem medo de falta de energia).

1.9 O DelayQueue tem algum requisito para elementos? Posso colocar String na fila?
Resposta : DelayQueue exige que os elementos implementem a interface Atrasada e o próprio Atrasado implemente a interface Comparável.O papel da interface Atrasada é definir por quanto tempo o tempo limite será atingido e personalizar o período de tempo limite dos usuários. A interface comparável é usada principalmente para o interelemento A classificação do tempo limite, a combinação dos dois, pode tornar os elementos que expiram mais cedo na frente.

Portanto, não é aceitável colocar String em DelayQueue e a compilação não será aprovada.Quando a classe DelayQueue é definida, ela é definida por um tipo genérico.O tipo genérico deve ser uma subclasse da interface Atrasada.

1.10 Como o DelayQueue permite que os elementos que expiram em breve sejam executados primeiro?
Resposta : Os elementos em DelayQueue implementam interfaces Delayed e Comparable, que usarão o método CompareTo de Sortable para classificar.Podemos usar essa função para implementar a diferença entre o tempo de expiração e o tempo atual no método compareTo, portanto, quanto mais cedo os elementos expirados Quanto menor a diferença calculada, mais cedo será executada.

1.11 Como verificar o tamanho do SynchronousQueue?
Resposta : Esta pergunta é uma armadilha. A pergunta primeiro define o SynchronousQueue para verificar o tamanho. De fato, o próprio SynchronousQueue não tem capacidade, portanto, não pode verificar o tamanho de sua capacidade. Seu método de tamanho interno é retornar à morte. 0

1.12 Existem várias estruturas de dados na parte inferior do SynchronousQueue, qual é a diferença entre as duas?
Resposta : Existem dois tipos de estruturas de dados na camada inferior, ou seja, fila e pilha.

A diferença entre os dois: a
fila mantém a ordem de entrada, saída, de modo que os elementos mais avançados a serem desenfileirados serão consumidos primeiro, o que chamamos de justos, e a pilha é a ordem de entrada, saída e os dados que entram na pilha primeiro Pode ser consumido no final, o que chamamos de injusto.
A estrutura de dados dos dois é diferente, o que leva a diferenças nos métodos take e put.Para obter detalhes, consulte o capítulo "SynchronousQueue Source Code Analysis".

1.13 Supondo que a parte inferior do SynchronousQueue use uma pilha, o thread 1 é bloqueado pela operação take e o thread 2. executa a operação put.Como o thread 2 passa os dados put nesse momento?
Resposta : Essa é uma boa pergunta e também é a questão central do entendimento do SynchronousQueue.

Primeiro, o encadeamento 1. está bloqueado.Neste momento, o cabeçalho da pilha é o encadeamento 1. Nesse momento, o encadeamento 2 realiza uma operação de put e os dados put são atribuídos ao atributo de correspondência do cabeçalho da pilha e o encadeamento 1 é ativado. Depois que o encadeamento 1 é despertado, ele obtém Com o atributo match no cabeçalho da pilha, você pode obter os dados de colocação.

Estritamente falando, não é que a operação put transfira diretamente os dados para a tomada, mas a operação put altera os dados do cabeçalho da pilha, para que a tomada possa obter diretamente os dados do cabeçalho da pilha, e o cabeçalho da pilha é o meio de comunicação entre as operações take e put .

1.14 Se você deseja usar uma fila de tamanho fixo, existem vários tipos de filas para escolher: qual é a diferença?
Resposta : LinkedBlockingQueue e ArrayBlockingQueue podem ser usados.

A primeira é uma lista vinculada e a segunda é uma matriz.Quando a lista vinculada é adicionada, desde que a associação entre os novos dados e os dados finais seja estabelecida, a posição do índice precisa ser considerada quando a matriz é adicionada (takeIndex e putIndex são registrados separadamente Pegue o índice dos dados e coloque o índice dos dados); se aumentar para a última posição da matriz, começará a ser adicionado novamente na próxima vez.

1.15 O ArrayBlockingQueue pode ser expandido dinamicamente? O que fazer quando a última posição da matriz é usada?
Resposta : Não, embora a camada inferior de ArrayBlockingQueue seja uma matriz, ela não pode ser expandida dinamicamente.

Supondo que a operação de colocação use a última posição da matriz, a próxima colocação precisará reiniciar a partir da posição da matriz 0.

Supondo que a operação de captura use a última posição da matriz, a próxima captura começará da posição da matriz 0 novamente.

1.16 Como o ArrayBlockingQueue pega e coloca a posição do índice? É calculado usando o algoritmo de hash?
Resposta : ArrayBlockingQueue possui dois atributos, takeIndex e putIndex, que identificam respectivamente a posição do próximo take e put. Cada vez que take e put são concluídos, eles serão aumentados em um. Embora a camada inferior seja um array, é diferente do HashMap e não é passada. Calculado pelo algoritmo de hash.

2 Resumo

As filas são a base de APIs complexas, como bloqueios e conjuntos de encadeamentos. Muitos entrevistadores solicitarão o conhecimento de filas ao solicitar essas APIs. Se você não responder bem, o entrevistador poderá pensar que você usou apenas bloqueios e conjuntos de encadeamentos. No entanto, os princípios e a implementação subjacentes não são totalmente compreendidos, portanto a fila ainda é muito importante, mas o código-fonte da fila é mais complicado.Recomenda-se que você tente o método de depuração para entender o código-fonte.

Publicado 40 artigos originais · ganhou elogios 1 · vista 4982

Acho que você gosta

Origin blog.csdn.net/aha_jasper/article/details/105525836
Recomendado
Clasificación