Os pools de threads podem executar várias tarefas simultaneamente. Às vezes, podemos querer rastrear os resultados da execução das tarefas. Mesmo dentro de um certo período de tempo, se a tarefa não for concluída, também podemos cancelar a execução de tarefas. Para apoiar esse recurso, o ThreadPoolExector fornece o FutureTask para rastrear a execução e o cancelamento das tarefas. Este artigo apresenta o princípio de implementação do FutureTask.
Para entender melhor o princípio da implementação do FutureTask, primeiro fornecemos várias interfaces e estruturas de classe importantes, como mostrado na figura abaixo:
ThreadpoolExecutor fornece a interface de envio para enviar tarefas. Enviar suporta duas interfaces diferentes: Runnable e Callable. Para fornecer uma interface externa unificada, o JDK envolve internamente o Runnable em um chamável, o que é implementado através do adaptador RunnableAdapter. A seguir, o código -fonte do RunnableAdapter:
Classe final estática runnableAdApter <T> implementa o Callable <T> {Final Runnable Task; resultado T final; RunnableAdApter (tarefa executável, resultado t) {this.task = tarefa; this.result = resultado; } public t Call () {Task.run (); resultado de retorno; }}RunnableAdApter é a classe de implementação do Callable, que implementa o método de chamada. O método de chamada simplesmente chama Task.Run () e, em seguida, retorna o resultado, o que garante que apenas a interface chamada precise ser tratada uniformemente internamente.
Através da seção anterior, sabemos que a tarefa executável enviada é convertida internamente em tarefas chamáveis. Verifique o valor de retorno do método de envio, que é um futuro. De fato, esse futuro é uma instância do FutureTask. Através desta instância, chamar o método get pode bloquear o thread atual até que a tarefa seja concluída e o resultado seja retornado.
Toda a cadeia de chamadas se parece com o seguinte:
Tópico do trabalhador -> futureTask.run () -> callable.call () -> task.run ()
Se a tarefa chamável for enviada, existem apenas as três primeiras chamadas.
Para demonstrar melhor todo o processo, os exemplos a seguir serão usados para demonstrar o processo de execução.
1. Envie uma tarefa chamada ao pool de threads (o Runnable também será convertido em chamadas). No momento, o chamável é passado para uma instância do FutureTask, como mostrado abaixo:
2. O pool de threads usa um thread para executar a tarefa FutureTask.
O processo de execução de tarefas é relativamente simples. No final, o método Callable.Call () ou Runnable.run () será chamado, e será obtido um resultado, o que armazenará o resultado na propriedade do resultado da instância do FutureTask, e o status será modificado para o normal, indicando que a tarefa foi executada e o resultado pode ser obtido.
Assumimos que vários threads chamam o método get da mesma instância do FutureTask durante a execução do callable.call() . Neste momento, esses threads serão bloqueados e armazenados em uma pilha, como mostrado na figura abaixo:
Os threads 1, 2 e 3 chamam FutureTask.get . Como a tarefa não foi executada, todos os três threads serão bloqueados e sonolentos. Há uma pilha no FutureTask para armazenar tópicos em espera. O ponteiro superior da pilha é referenciado pelo FutureTask.waiters . Quando a tarefa é executada, os threads em toda a pilha iteram. No momento, cada encadeamento será despertado e o resultado da execução da tarefa pode ser obtido com sucesso (o resultado da execução é armazenado no FutureTask.outcome) .
O FutureTask também suporta a função de cancelamento das tarefas, todas as quais coordenam vários threads através do estado do FutureTask.
A interface FutureTask é um mecanismo de implementação que nos fornece rastreamento e controle da execução de tarefas. Comparado com o próprio pool de threads, é relativamente simples e acredito que não é difícil de entender.
O exposto acima é todo o conteúdo deste artigo sobre o princípio da implementação do FutureTask no Java Thread Pool. Espero que seja útil para todos. Amigos interessados podem continuar se referindo a outros tópicos relacionados neste site. Se houver alguma falha, deixe uma mensagem para apontá -la. Obrigado amigos pelo seu apoio para este site!