Thread

Galera olhem esse codigo

package client;

import javax.swing.JOptionPane;

public class Class1
{
  public Class1()
  {
    Thread t = new Thread(new Run("Thread 1"), "Sempre");
    t.start();
    Thread t1 = new Thread(new Run("Thread 2"), "Sempre");
    t1.start();
  }

  public static void main(String[] args)
  {
    new Class1();


  }

  class Run
    implements Runnable
  {
    private String nome;

    Run(String x)
    {
      nome = x;
    }

    public void run()
    {
     
      while (true)
      {
        try
        {
          Thread.sleep(100);
        }
        catch (InterruptedException e)
        {
          // TODO
        }
        System.out.println(nome + " : " + Math.random() * 100);
      }
    }
  }
}

Olha como esta saindo o resultado:

Thread 2 : 7.300497875002298
Thread 1 : 89.23030632052101
Thread 2 : 26.27769061525961
Thread 1 : 28.67944254186202
Thread 1 : 60.935482085554014
Thread 2 : 10.163166920967637
Thread 1 : 97.18875484988338
Thread 2 : 10.730325834085463
Thread 2 : 64.91071621725114
Thread 1 : 80.99685353826263
Thread 1 : 31.82829461323221
Thread 2 : 61.35872212132101
Thread 1 : 31.944223142569083
Thread 2 : 21.191124573317655
Thread 2 : 36.64968339744674
Thread 1 : 27.714034946688216
Thread 1 : 21.076466113955906
Thread 2 : 37.6212754543789
Thread 2 : 79.56254279039905
Thread 1 : 35.280417821696794
Thread 1 : 86.8420735678996
Thread 2 : 35.94328652240012
Thread 1 : 96.75562232405247

O correto nao seria 1 sim outro nao um sim outro nao? Como fazer isso?

Você nunca saberá a ordem em que as Threads serão executadas, tudo depende da implementação da VM… Como diz o livro da Kathy Sierra (SCJP) quando trata-se the Threads há poucas garantias.

Você nunca pode ter certeza que as theads vão rodar bonitinhas, uma a cada "Thread.sleep(100); "

Só com semáforo que eu consigo fazer isso: uma váriavel que diz de quem é a vez de “imprimir”.

Você pode sim controlar a ordem das Threads nesse caso.

Utilize um esquema de wait() e notify(). Dê uma pesquisada por aí que você vai encontrar bons exemplos.

hehehe Ué, e isto não é um semáforo?? :smiley:

semáforo?? tecnicamente seria assim mesmo? ou isso e uma giria popular que damos a algum tipo de POG??

O esquema é o mesmo.

Acontece que eu falei de wait e notify, que é a mais comum. Mas há a classe java.util.concurrent.Semaphore (que também é um tipo válido de solução). Outra solução válida seria a utilização de travas explícitas.

teitei, semáforo é sério mesmo hahahahahah

Tem em qualquer livro de Sistemas Operacionais, acho que foi até o Dijkstra que o definiu.

[quote=cesarherrera]Você nunca saberá a ordem em que as Threads serão executadas, tudo depende da implementação da VM…
[/quote]

Não é da implementação da VM, mas sim do SO. A VM delega o escalonamento para o SO.

Nesse sentido, prefiro dizer que não há absolutamente nenhuma garantia…

Teitei, o que você deve ter em mente é que um bom SO vai tentar escalonar essas threads estatisticamente em 50% do tempo para cada uma. Como ele faz isso é a cargo dele. Um mal SO não vai ser tão justo assim.

[quote=felipealbuquerque]Você pode sim controlar a ordem das Threads nesse caso.
Utilize um esquema de wait() e notify(). Dê uma pesquisada por aí que você vai encontrar bons exemplos.[/quote]

Só tem um cuidado aí.

Nesse caso as threads percorrem objetos diferentes, por isso, só usar os métodos com modificador synchronized, wait e notify não adiantaria.

Para que ele pudesse usar wait e notify ele teria que fazer o seguinte:

  1. Criar um objeto compartilhado por ambas as threads e usar o synchronized, wait e notify nesse objeto (nada mais é do que usar um lock explícito. Poderia fazer isso compatilhando um objeto da classe Lock também.);
  2. Usar as duas threads sobre o mesmo Runnable;

Esse é um erro que pega muita gente que está começando com threads.

É claro que controlar as threads dessa forma seria estúpido. Se você quer rodar um método seguido de outro, é melhor criar os dois runnables e fazer assim:

[code]Run run1 = new Run();
Run run2 = new Run();

Thread t = new Thread() {
@Override
public void run() {
run1.run();
run2.run();
}
}

t.start();
[/code]

Isso ainda poupa recursos do SO, pois não é de graça criar e manter threads.