samples/reentrant/src/org/apidesign/reentrant/CriticalSectionReentrantForLoop.java
1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/samples/reentrant/src/org/apidesign/reentrant/CriticalSectionReentrantForLoop.java Sat Jun 14 09:54:37 2008 +0200
1.3 @@ -0,0 +1,42 @@
1.4 +package org.apidesign.reentrant;
1.5 +
1.6 +import java.util.Collection;
1.7 +import java.util.concurrent.atomic.AtomicInteger;
1.8 +
1.9 +public class CriticalSectionReentrantForLoop<T extends Comparable<T>> implements CriticalSection<T> {
1.10 + private volatile T pilot;
1.11 + private AtomicInteger cnt = new AtomicInteger();
1.12 +
1.13 + public void assignPilot(T pilot) {
1.14 + this.pilot = pilot;
1.15 + }
1.16 +
1.17 + // BEGIN: reentrant.merge.for
1.18 + public int sumBigger(Collection<T> args) {
1.19 + T pilotCopy = this.pilot;
1.20 + for (;;) {
1.21 + int previous = cnt.get();
1.22 + int own = doCriticalSection(args, pilotCopy);
1.23 + // if there was no parallel or reentrant change,
1.24 + // apply and return. Otherwise try once more.
1.25 + if (cnt.compareAndSet(previous, own + previous)) {
1.26 + return own;
1.27 + }
1.28 + }
1.29 + }
1.30 + // END: reentrant.merge.for
1.31 +
1.32 + private int doCriticalSection(Collection<T> args, T pilotCopy) {
1.33 + int own = 0;
1.34 + for (T cmp : args) {
1.35 + if (pilotCopy.compareTo(cmp) < 0) {
1.36 + own++;
1.37 + }
1.38 + }
1.39 + return own;
1.40 + }
1.41 +
1.42 + public int getCount() {
1.43 + return cnt.get();
1.44 + }
1.45 +}