package chapter21;//: concurrency/OrnamentalGarden.java
import java.util.concurrent.*;
import java.util.*;
import static net.mindview.util.Print.*;
/***
* 花园委员会希望了解每天通过多个大门进入公园的总人数,一个共享资源的demo
* 每个大门都有一个十字转门或某种形式的计数器,并且任何一个十字转门的计数值递增时表示公园中总人数的共享计数值也会递增
*/
class Count {
private int count = 0;//实现跟踪花园参观者的主计数值
private Random rand = new Random(47);
// Remove the synchronized keyword to see counting fail:
public synchronized int increment() {//多个任务会同时访问并修改count 不加synchronized 程序会anr
int temp = count;
if(rand.nextBoolean()) // Yield half the time 1/2的时间在产生乱步
Thread.yield();
return (count = ++temp);
}
public synchronized int value() { return count; }
}
class Entrance implements Runnable {
private static Count count = new Count();
private static List<Entrance> entrances =
new ArrayList<Entrance>();
private int number = 0;//每个入口进入公园的人数
// Doesn't need synchronization to read:
private final int id;
private static volatile boolean canceled = false;
// Atomic operation on a volatile field:
public static void cancel() { canceled = true; }
public Entrance(int id) {
this.id = id;
// Keep this task in a list. Also prevents
// garbage collection of dead tasks:
entrances.add(this);
}
public void run() {
while(!canceled) {
synchronized(this) {
++number;
}
print(this + " Total: " + count.increment());
try {
TimeUnit.MILLISECONDS.sleep(100);
} catch(InterruptedException e) {
print("sleep interrupted");
}
}
print("Stopping " + this);
}
public synchronized int getValue() { return number; }
public String toString() {
return "Entrance " + id + ": " + getValue();
}
public static int getTotalCount() {
return count.value();
}
public static int sumEntrances() {
int sum = 0;
for(Entrance entrance : entrances)
sum += entrance.getValue();
return sum;
}
}
public class OrnamentalGarden {
public static void main(String[] args) throws Exception {
ExecutorService exec = Executors.newCachedThreadPool();
for(int i = 0; i < 5; i++)
exec.execute(new Entrance(i));
// Run for a while, then stop and collect the data:
TimeUnit.SECONDS.sleep(3);
Entrance.cancel();
exec.shutdown();
if(!exec.awaitTermination(250, TimeUnit.MILLISECONDS))
print("Some tasks were not terminated!");
print("Total: " + Entrance.getTotalCount());
print("Sum of Entrances: " + Entrance.sumEntrances());
}
}
04-01
432
![](https://csdnimg.cn/release/blogv2/dist/pc/img/readCountWhite.png)
04-01
494
![](https://csdnimg.cn/release/blogv2/dist/pc/img/readCountWhite.png)