【发布时间】:2019-07-08 17:38:09
【问题描述】:
我想使用 4 个线程和信号量来实现 FizzBizz 游戏。
我设法使线程以所需的顺序工作:fizz() -> buzz() -> fizzBuzz() -> printNumber().
但是,我无法使整个过程循环。
每个方法都有自己的信号量,尽管在释放下一个方法信号量之前锁定了自己的信号量,但这些方法不会挂在第二个获取上(实际上这是方法中的第一个)。
期望的行为:
1. 锁定所有信号量。
2. 启动所有 4 种方法。
3.释放fizz()信号量,让它先行。
4. fizz() 完成,释放buzz() 锁并挂起,直到printNumber() 释放它。
5.等
import java.util.concurrent.Semaphore;
import java.util.concurrent.atomic.AtomicLong;
class FizzBuzz {
protected AtomicLong num = new AtomicLong(1);
protected AtomicLong n = new AtomicLong(100);
protected Semaphore sem1 = new Semaphore(1);
protected Semaphore sem2 = new Semaphore(1);
protected Semaphore sem3 = new Semaphore(1);
protected Semaphore sem4 = new Semaphore(1);
public void start() {
System.out.println("Started");
try {
sem1.acquire();
sem2.acquire();
sem3.acquire();
sem4.acquire();
this.fizz();
this.buzz();
this.fizzBuzz();
this.printNumber();
sem1.release();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
public void fizz() {
new Thread() {
@Override
public void run() {
while (num.get() <= n.get()) {
try {
// System.out.println("Fizz waiting...");
sem1.acquire();
sem1.release();
if (num.get() > n.get()) {
break;
}
if (num.get() % 3 == 0 && num.get() % 5 != 0) {
num.getAndIncrement();
System.out.println("Fizz");
}
sem1.acquire();
sem2.release();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}.start();
}
public void buzz() {
new Thread() {
@Override
public void run() {
while (num.get() <= n.get()) {
try {
// System.out.println("Buzz waiting...");
sem2.acquire();
sem2.release();
if (num.get() > n.get()) {
break;
}
if (num.get() % 5 == 0 && num.get() % 3 != 0) {
num.getAndIncrement();
System.out.println("Buzz");
}
sem2.acquire();
sem3.release();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}.start();
}
public void fizzBuzz() {
new Thread() {
@Override
public void run() {
while (num.get() <= n.get()) {
try {
// System.out.println("FizzBuzz waiting...");
sem3.acquire();
sem3.release();
if (num.get() > n.get()) {
break;
}
if (num.get() % 3 == 0 && num.get() % 5 == 0) {
num.getAndIncrement();
System.out.println("FizzBuzz");
}
sem3.acquire();
sem4.release();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}.start();
}
public void printNumber() {
new Thread() {
@Override
public void run() {
while (num.get() <= n.get()) {
try {
// System.out.println("Print Number waiting...");
sem4.acquire();
sem4.release();
if (num.get() > n.get()) {
break;
}
if (num.get() % 3 == 1 && num.get() % 5 == 1) {
num.getAndIncrement();
System.out.println(num);
}
sem4.acquire();
sem1.release();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}.start();
}
}
【问题讨论】:
标签: java concurrency semaphore