Dúvida com Threads

4 respostas
eltonk

Pessoal,

Tendo como referência o código abaixo, e vendo a saída do código me surgiu uma dúvida…

Em primeiro lugar eu crio e e "starto" as threads t e t2…
Em t, tenho a chamada para "Thread.yield();" devolvendo a thread para Runnable e iniciando t2 (que estava em Runnable tb)…

Espero t2 terminar o processamento para que a thread main continue a execução ( com o t2.join():wink:

É agora que vem a dúvida…
Em seguida eu crio e "starto" a thread 3 e aguardo um notify (através de t3.wait():wink:
O sistema executa a t3, notifica a thread main e somente depois disso tudo que a primeira thread t termina a execução…

No meu ponto de vista, a thread t deveria executar antes da t3, porque ela estava no pool com o status runnable. :shock:

Ainda fiz o teste e mudei a prioridade da thread t como máxima prioridade, e mesmo assim a diaba é a última a executar…

Alguem tem idéia do que está acontecendo?! :roll:

package chap9;

public class ThreadTeste {
    public static void main(String[] ar) {

         MinhaThread m = new MinhaThread();
         MinhaThread2 m2 = new MinhaThread2();
         
         Thread t = new Thread(m);
         Thread t2 = new Thread(m2);
         
         System.out.println("vai comecar.....................................");
         t.start();
         t2.start();
         
         try {
             t2.join();
         } catch (InterruptedException e) {
             e.printStackTrace();
         }
         System.out.println("passou a thread2.................................");
         
         MinhaThread3 m3 = new MinhaThread3();
         Thread t3 = new Thread(m3);
         System.out.println("iniciando thread 3 ..............................");
         t3.start();
         
         synchronized (t3) {
            try {
                System.out.println("esperando thread 3 ..............................");
                t3.wait();
                System.out.println("esperou thread 3 ..............................");
            } catch (InterruptedException e) {
                System.out.println("ie");
                e.printStackTrace();
            }

        }
    }
}

class MinhaThread implements Runnable {
    public void run() {
        for (int i = 0; i &lt 10; i++) {
            System.out.println("i = " + i);
            Thread.yield();
        }
    }
}

class MinhaThread2 implements Runnable {
    public void run() {
        for (int i = 0; i &lt 10; i++) {
            System.out.println("j = " + i);
        }
    }
}

class MinhaThread3 implements Runnable {
    public void run() {
        synchronized (this) {
            for (int i = 0; i &lt 10; i++) {
                System.out.println("k = " + i);
            }
            notify();
        }
    }
}

e a saida que sempre vem é:

vai comecar.....................................
i = 0
j = 0
j = 1
j = 2
j = 3
j = 4
j = 5
j = 6
j = 7
j = 8
j = 9
passou a thread2.................................
iniciando thread 3 ..............................
esperando thread 3 ..............................
k = 0
k = 1
k = 2
k = 3
k = 4
k = 5
k = 6
k = 7
k = 8
k = 9
esperou thread 3 ..............................
i = 1
i = 2
i = 3
i = 4
i = 5
i = 6
i = 7
i = 8
i = 9

4 Respostas

eltonk

Pessoal…

modifiquei uma das classes para:

class MinhaThread3 implements Runnable {
    public void run() {
        synchronized (this) {
            for (int i = 0; i &lt 10; i++) {
                System.out.println("k = " + i);
                if (i == 5){
                  try {
                      System.out.println("vai esperar um pouco k");
                     wait(2000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                }
            }
            notify();
        }
    }
}

E deste modo consegui comprovar que não é bizarrice, mas uma variável estocástica :stuck_out_tongue:

Mas ainda ficou a dúvida das prioridades… Se seto t com máxima prioridade e t3 com mínima prioridade, não altero os dados coletados… :roll:

Abraços…

J

Isso é bom pra você saber que não existe nenhum tipo de garantia sobre prioridade ou qual Thread irá executar primeiro, quem decide isso é o sistema operacional e não adianta tentar intervir.

Se o SO achou que deveria executar a Thread t3 antes da t, não tente contraria-lo.

:wink:

eltonk

jairelton:
Isso é bom pra você saber que não existe nenhum tipo de garantia sobre prioridade ou qual Thread irá executar primeiro, quem decide isso é o sistema operacional e não adianta tentar intervir.

Se o SO achou que deveria executar a Thread t3 antes da t, não tente contraria-lo.

:wink:

Pois então Jair…
Que as garantias eram paraguaias eu sabia, mas agora o que me deixa com a pulga atrás da orelha é setar máxima prioridade para uma e mínima para outra e mesmo assim o S.O não me obedecer… :stuck_out_tongue:

ViniGodoy

Normalmente o SO respeita as prioridades… porém, quando e como ele fará isso é a cargo dele.

Alguns SOs podem decidir respeitar as prioridades apenas se o processador estiver carregado. Se houver muito processamento ocioso, não tem porque forçar que uma thread rode mais lentamente que a outra.

Alguns SOs são autorizados a desprezar totalmente a prioridade das threads.

Uma coisa perigosa: Alguns SOs podem, por exemplo, garantir que não ocorra starvation (uma thread de baixíssima prioridade não executar nunca). Outros não.

É até por isso que alguns livros de threads em java recomendam que não altere-se a prioridade das threads. Pelo menos, não muito. Se você quer um sistema que realmente funcione em todos os SOs, não pode correr risco de starvation.

Criado 8 de março de 2007
Ultima resposta 8 de mar. de 2007
Respostas 4
Participantes 3