如何在Java中的两个线程之间创建竞争情境?

时间:2017-11-11 20:01:34

标签: java multithreading junit

我想测试一个用作Id计数器的同步方法。为了测试给定方法返回的ID的唯一性,我想在两个线程之间创建种族情况,这两个线程将同时调用给定方法 。我怎么能实现这个目标呢?

class Counter{
    private static int nextId = 1;
    public static synchronized int nextId() {
        int id = nextId;
        nextId += 1;
        return id;
    }
}

3 个答案:

答案 0 :(得分:3)

无法在发布的代码上创建竞争条件。 可变共享状态是私有静态height of its tallest subtree + 1变量, 并且它由类实例的内在锁保护。 没有两个线程可以进入同步folde方法, 因此不可能出现竞争条件。

答案 1 :(得分:0)

您可以执行以下操作来创建两个线程并让它们从Counter类中获取新的ID:

Thread t1= new Thread(){
    public void run(){
      for(int i=0; i<1000; i++){
          System.out.println("T1: "+Counter.nextId());
      }
    }
  }

  t1.start();

Thread t2= new Thread(){
    public void run(){
      for(int i=0; i<1000; i++){
          System.out.println("T2: "+Counter.nextId());
      }
    }
  }

  t2.start();

答案 2 :(得分:0)

这将生成竞争条件。运行此程序几次。在大多数时间每次都会给出不同的结果。这只适用于java版本1.8或1.8 +。对于低于1.8的java版本使用Runnable匿名类而不是lambda表达式。

       public class Main {
   public static void main(String[] args) {
        new Thread(()-> {
            Random rand = new Random();
            for(int i=0;i<1000;i++) {
                System.out.println(Counter.nextId());
                try {
                    Thread.sleep(rand.nextInt(10));
                } catch (InterruptedException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
            }
        }).start();

        new Thread(()-> {
            Random rand = new Random();
            for(int i=0;i<1000;i++) {
                System.out.println(Counter.nextId());
                try {
                    Thread.sleep(rand.nextInt(10));
                } catch (InterruptedException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
            }
        }).start();
    }
}
class Counter{
private static int nextId = 1;
public static  int nextId() {
    int id = nextId;
    nextId += 1;
    return id;
 }
}