题目类型:并发
题目:打印零与奇偶数
题目描述:
相同的一个 ZeroEvenOdd 类实例将会传递给三个不同的线程:
线程 A 将调用 zero(),它只输出 0 。
线程 B 将调用 even(),它只输出偶数。
线程 C 将调用 odd(),它只输出奇数。
每个线程都有一个 printNumber 方法来输出一个整数。请修改给出的代码以输出整数序列 010203040506... ,其中序列的长度必须为 2n。
1 class ZeroEvenOdd { 2 private int n; 3 private boolean zeroTag = true;// true:打印0,false:打印非0 4 private int number = 0;// 累加数字 5 private Object lock = new Object(); 6 7 public ZeroEvenOdd(int n) { 8 this.n = n; 9 } 10 11 // printNumber.accept(x) outputs "x", where x is an integer. 12 public void zero(IntConsumer printNumber) throws InterruptedException { 13 for (int j = 1; j <= n; j++) { 14 synchronized (lock) { 15 while (!zeroTag) { 16 lock.wait(); 17 } 18 printNumber.accept(0); 19 zeroTag = false; 20 number = j; 21 lock.notifyAll(); 22 } 23 } 24 } 25 26 public void even(IntConsumer printNumber) throws InterruptedException { 27 for (int j = 2; j <= n; j = j + 2) { 28 synchronized (lock) { 29 while (zeroTag || number != j) { 30 lock.wait(); 31 } 32 printNumber.accept(j); 33 zeroTag = true; 34 lock.notifyAll(); 35 } 36 } 37 } 38 39 public void odd(IntConsumer printNumber) throws InterruptedException { 40 for (int j = 1; j <= n; j = j + 2) { 41 synchronized (lock) { 42 while (zeroTag || number != j) { 43 lock.wait(); 44 } 45 printNumber.accept(j); 46 zeroTag = true; 47 lock.notifyAll(); 48 } 49 } 50 } 51 }