2014-02-22 43 views
0

我想同时运行两个不同运行方法的线程。可能吗?我在下面有简单的代码,但它们不兼容。我只想每5秒运行第一个线程,并且总是运行第二个线程。两个线程不同运行方法并行工作

public static int x = 0; 

public static void main(String[] args) throws InterruptedException{ 

    Runnable r1 = new Runnable() { 
     public void run() { 
      x = x + 1; 
      System.out.println("increment x"); 
     } 
    }; 

    Runnable r2 = new Runnable() { 
     public void run() { 
      System.out.println("x is "+x); 
     } 
    }; 

    while(true){ 
     Thread t1 = new Thread(r1); 
     Thread t2 = new Thread(r2); 
     t1.start(); 
     t2.start(); 
     t1.sleep(5000); 
    } 
} 
+0

a)您不应该无限循环地开始运行已经线程。 b)您不会同步对x的访问。 c)并发控制台输出会导致问题。 – deviantfan

+0

3)Thread.sleep()是静态的,可以让* current *线程,而不是被引用线程sleep(与静态方法一样,没有这种东西) –

回答

-1
public class Test { 
public static int x = 0; 

public static void main(String[] args) throws InterruptedException{ 

    Runnable r1 = new Runnable() { 
     public void run() { 
      while(true){ 
      x = x + 1; 
      System.out.println("increment x"); 
      try { 
       Thread.sleep(5000); 
      } catch (InterruptedException e) { 
       // TODO Auto-generated catch block 
       e.printStackTrace(); 
      } 
      } 
     } 
    }; 

    Runnable r2 = new Runnable() { 
     public void run() { 
      while(true){ 
      System.out.println("x is "+x); 
      } 
     } 
    }; 
     Thread t1 = new Thread(r1); 
     Thread t2 = new Thread(r2); 
     t1.start(); 
     t2.start(); 

//的Thread.sleep (5000);

} 

}

是这样的..但保持在上述

+1

请给出解释。 –

+0

这只是为了展示它应该如何工作。像这样访问一个静态变量可能会导致错误。两个线程可能会同时使用相同的变量,导致不可预知的结果。为了避免使用与下面解释的@JB同步。 – user3340677

3

您的run()方法只增加x,打印它并返回。只要run方法返回,线程就会停止运行。如果您想要永远运行某些东西,则需要在run()方法中使用循环。而且,在没有任何同步的情况下访问共享变量将不会导致可预测的结果。你的x变量应该至少是易变的。最后,Thread.sleep()是一个静态方法。因此,应使用类名叫做:

Thread.sleep(5000L); 

它使当前线程睡眠。

下面是一个例子,其中一个线程增量X每500毫秒时间,一个其他线程打印X每100毫秒时间,并且两个线程都在5秒钟后中断:

public class ThreadExample { 
    private static volatile int x; 

    private static class Incrementer implements Runnable { 
     @Override 
     public void run() { 
      while (!Thread.currentThread().isInterrupted()) { 
       x++; 
       try { 
        Thread.sleep(500L); 
       } 
       catch (InterruptedException e) { 
        return; 
       } 
      } 
     } 
    } 

    private static class Reader implements Runnable { 
     @Override 
     public void run() { 
      while (!Thread.currentThread().isInterrupted()) { 
       System.out.println(x); 
       try { 
        Thread.sleep(100L); 
       } 
       catch (InterruptedException e) { 
        return; 
       } 
      } 
     } 
    } 

    public static void main(String[] args) throws InterruptedException { 
     Thread t1 = new Thread(new Incrementer()); 
     Thread t2 = new Thread(new Reader()); 
     t1.start(); 
     t2.start(); 

     try { 
      Thread.sleep(5000L); 
     } 
     finally { 
      t1.interrupt(); 
      t2.interrupt(); 
     } 
    } 
} 
+0

但是,如果我在run方法中添加while循环,当第一个线程t1)开始运行,第二个(t2)永远不会开始运行。 – user1914367

+1

你为什么这么认为?线程的全部要点是能够同时运行。你的程序目前启动数十个线程,每个线程都执行一个或两个操作:增加x并打印它。 –

+0

这不是你想要的吗?如果不是,请解释你想要的。第一个线程应该增加5秒钟的值并在什么时候停止?第二个线程应该连续打印值并在什么时候停止?线程是否应该自行停止运行,或者主线程是否要求它们停止运行,如果是,何时运行? –

0

在while循环做心灵点,你每次创建新Threads然后start他们每个人说的就是为什么你有这样行为。

然后,你将需要移动while循环线程内,使他们LOOL象下面这样:

public static volatile int x = 0; 

public static void main(String[] args) throws InterruptedException{ 

Runnable r1 = new Runnable() { 
    public void run() { 
     while (true) { 
     x = x + 1; 
     System.out.println("increment x"); 
     this.sleep(5000); 
     } 
    } 
}; 

Runnable r2 = new Runnable() { 
    public void run() { 
     while(true){ 
     System.out.println("x is "+x); 
     } 
    } 
}; 
Thread t1 = new Thread(r1); 
Thread t2 = new Thread(r2); 
t1.start(); 
t2.start(); 
} 

还请注意,您的x变量应该同步存取看到正确的值。

BR。

+0

此代码仍有问题。至少变量x需要是易失性的或最终AtomicInteger用于线程同步。 – wonhee

+1

同步的目标不是避免死锁。目标是能够看到正确的价值。没有同步的代码永远不会死锁。但它会显示不正确的结果。 –

0
Thread t1;; 
    Thread t2; 
while(true){ 
     t1 = new Thread(r1); 
     t2= new Thread(r2); 
     t1.start(); 
     t1.sleep(5000); 
     t2.start(); 

} 

你正在添加的代码是正确的把代码放在t2.sleep(5000)t2.start()之前。

相关问题