1. junte-se ao tópico :
Durante a execução do thread, às vezes você deseja que outro thread seja executado primeiro, como dividir um grande problema em muitos pequenos problemas, atribuindo threads a cada pequeno problema, mas depois que todos os pequenos problemas forem processados, deixe o thread principal realizar outras operações. Neste momento, podemos chamar o método join() de outros threads no thread principal para bloquear o thread de chamada (aqui, o thread principal).
Código de exemplo:
Copie o código do código da seguinte forma:
pacoteorg.frzh.thread;
classe pública JoinThread estende Thread{
//Fornece um construtor parametrizado para definir o nome do thread
public JoinThread(Nome da string) {
super(nome);
}
execução void pública() {
for (int i = 0; i < 100; i++) {
System.out.println(getNome() + " " + i);
}
}
public static void main(String[] args) {
//Iniciar thread filho
new JoinThread("novo tópico").start();
for (int i = 0; i < 100; i++) {
se (eu == 20) {
JoinThread jt = new JoinThread("tópico a ser unido");
jt.start();
//O thread principal chama o método join do thread jt, então o thread principal deve esperar que jt termine de ser executado antes de poder executar
tentar {
jt.join();
} catch (InterruptedException e) {
// TODO Bloco catch gerado automaticamente
e.printStackTrace();
}
}
System.out.println(Thread.currentThread().getName() + " " +i);
}
}
}
Originalmente, havia três conjuntos de threads (dois subthreads e um thread principal). Quando i = 20, o thread principal é bloqueado e precisa esperar até que o "thread unido" seja executado antes de ter a chance de ser executado. são apenas dois threads executados depois disso.
Três formas sobrecarregadas do método join():
join(): espera que o thread unido termine de ser executado;
join (long milis): O tempo mais longo de espera pela execução do thread unido é de milissegundos. Depois disso, mesmo que o thread unido não tenha terminado a execução, ele não esperará mais;
join (long milissegundos, int nanos): O tempo máximo de espera pela execução do thread unido é milis milissegundos + nanos microssegundos. (Este método é basicamente inútil).
2: Tópico de fundo :
Há um thread que é executado em segundo plano e sua tarefa é servir outros threads. Esse thread é chamado de "thread de segundo plano", "thread daemon" ou "thread elf". Quando todos os threads de primeiro plano morrerem, o thread de segundo plano morrerá automaticamente.
Código de exemplo:
Copie o código do código da seguinte forma:
pacoteorg.frzh.thread;
classe pública DaemonThread estende Thread{
execução void pública() {
for (int i = 0; i < 1000; i++) {
System.out.println(getNome() + " " +i);
}
}
public static void main(String[] args) {
DaemonThread dt = new DaemonThread();
//Define este tópico como um tópico de segundo plano
dt.setDaemon(verdadeiro);
dt.start();
for (int i = 0; i < 10; i++) {
System.out.println(Thread.currentThread().getName() + " " + i);
}
//O thread de primeiro plano termina, então o thread de segundo plano dt também terminará, portanto não será executado 999
}
}
O thread principal é padronizado para o thread de primeiro plano, os subthreads criados pelo thread de primeiro plano são padronizados para o thread de primeiro plano e os subthreads criados pelo thread de segundo plano são padronizados para o thread de segundo plano.
3. Thread sleep (sono):
O método de junção anterior permite que o thread de chamada espere que o thread unido termine de ser executado antes de continuar, enquanto o método sleep() permite que o thread de chamada seja bloqueado por um período de tempo antes de entrar novamente no estado pronto e esperar para ser agendado. Portanto, é frequentemente usado para pausar a execução do programa.
Código de exemplo:
Copie o código do código da seguinte forma:
pacoteorg.frzh.thread;
importar java.util.Date;
classe pública SleepThread{
public static void main(String[] args) {
for (int i = 0; i < 10; i++) {
System.out.println("Hora atual: " + nova Data());
tentar {
Thread.sleep(1000);
} catch (InterruptedException e) {
// TODO Bloco catch gerado automaticamente
e.printStackTrace();
}
}
}
}
Dois métodos de sobrecarga do método sleep():
static void sleep (long milis): deixa o thread atual pausar por milis milissegundos e entra no estado de bloqueio. Este método é afetado pela precisão e exatidão dos temporizadores do sistema e agendadores de threads.
suspensão estática vazia (milis longos, int nanos): pausa milissegundos + nanos microssegundos e entra no estado de bloqueio. Ele também será afetado pela precisão e exatidão do temporizador do sistema e do agendador de threads. Basicamente não é necessário.
4. Rendimento da rosca :
O método yield() é um pouco semelhante ao método sleep. Ele também pode pausar o thread em execução no momento, mas não bloqueará o thread, apenas o transferirá para o estado pronto (observe que não é um estado de bloqueio). O método yield() apenas dará a threads com a mesma prioridade ou prioridade mais alta uma chance de serem executados, portanto, um thread pode ser reprogramado para continuar a execução após chamar este método.
Código de exemplo:
Copie o código do código da seguinte forma:
pacoteorg.frzh.thread;
classe pública YieldThread estende Thread{
público YieldThread() {
}
public YieldThread(Nome da string) {
super(nome);
}
execução void pública() {
for (int i = 0; i < 100; i++) {
System.out.println(getNome() + " " +i);
se (eu == 20) {
//O thread atual produz
Thread.rendimento();
}
}
}
public static void main(String[] args) {
//Inicia duas threads simultâneas
YieldThread yt1 = new YieldThread("Avançado");
//Definir yt1 como a prioridade mais alta
yt1.setPriority(Thread.MAX_PRIORITY);
yt1.start();
YieldThread yt2 = new YieldThread("nível baixo");
yt2.setPriority(Thread.MIN_PRIORITY);
yt2.start();
/*
* Se a prioridade não estiver definida para o thread, a prioridade dos dois threads será a mesma, então os dois threads serão executados alternadamente, e quando o rendimento for chamado, o outro thread será executado;
* No entanto, após definir as prioridades acima para os dois threads respectivamente, a execução avançada do thread apenas será iniciada. Quando i = 20, o rendimento é chamado, mas porque o método rendimento só será iniciado.
* Dê oportunidades de execução para threads com a mesma prioridade ou prioridade mais alta, de modo que o thread de alto nível ainda esteja em execução neste momento e não seja concedido a threads de baixo nível
*/
}
}
5: Altere a prioridade do thread :
Isso é relativamente simples, basta chamar o método de instância setPriority(int prioridade) método. Cada thread tem como padrão a mesma prioridade de seu thread pai, e o thread principal tem como padrão a prioridade normal (5). Java fornece prioridades de 1 a 10 e você também pode usar três constantes estáticas:
MAX_PRIORITY:10
MIN_PRIORITY:1
NORM_PRIORITY:5
Nota: Embora Java forneça 10 prioridades, sistemas diferentes suportam prioridades diferentes, portanto, tente evitar o uso direto de números entre 1 e 10 e use constantes estáticas para garantir uma boa portabilidade.