Hinzufügen von Synchronisation und überwachten Warteschleifen
public
class GroundCounter {
protected long count_;
protected GroundCounter(long c) { count_ = c; }
protected long value_() { return count_; }
protected void inc_() { ++count_; }
protected void dec_() { --count_; }
}
public
class BoundedCounterVSC extends GroundCounter
implements
BoundedCounter {
public BoundedCounterVSC() { super(MIN); }
public synchronized long value() { return value_();
}
public synchronized void inc() {
while (value_() >= MAX)
try {
wait();
} catch(InterruptedException
ex) {};
inc_();
notifyAll();
}
public synchronized void dec() {
while (value_() <= MIN)
try {
wait();
} catch(InterruptedException
ex) {};
dec_();
notifyAll();
}
}
Umgehung
von Exceptions
public
class StackEmptyException extends Exception {}
public
class Stack { // fragments
public synchronized boolean isEmpty()
{/* ... */}
public synchronized void push(Object x)
{/* ... */}
public synchronized Object pop() throws
StackEmptyException {
if
(isEmpty())
throw
new StackEmptyException();
//
else ...
}
}
public
class WaitingStack extends Stack {
public synchronized void push(Object x)
{
super.push(x);
notifyAll();
}
public synchronized Object pop() throws
StackEmptyException {
while
(isEmpty())
try {
wait();
} catch(InterruptedException ex) {}
return
super.pop();
}
}
Readers and Writers
public
abstract class RW {
protected int activeReaders_ = 0; // threads executing read_
protected int activeWriters_ = 0; // always zero or one
protected int waitingReaders_ = 0; //
threads not yet in read_
protected int waitingWriters_ = 0; // same
for write_
protected abstract void read_(); //
implement in subclasses
protected abstract void write_();
public void read() {
beforeRead();
read_();
afterRead();
}
public void write() {
beforeWrite();
write_();
afterWrite();
}
protected boolean allowReader() {
return waitingWriters_ == 0 &&
activeWriters_ == 0;
}
protected boolean allowWriter() {
return activeReaders_ == 0 && activeWriters_
== 0;
}
protected synchronized void beforeRead() {
++waitingReaders_;
while
(!allowReader())
try { wait(); } catch
(InterruptedException ex) {}
--waitingReaders_;
++activeReaders_;
}
protected synchronized void
afterRead() {
--activeReaders_;
notifyAll();
}
protected synchronized void beforeWrite() {
++waitingWriters_;
while
(!allowWriter())
try { wait(); } catch
(InterruptedException ex) {}
--waitingWriters_;
++activeWriters_;
}
protected synchronized void afterWrite() {
--activeWriters_;
notifyAll();
}
}
Adapters
and Delegation
public
class BarePoint {
public double x, y;
}
public
class SynchedPoint {
protected BarePoint delegate_; // fixed,
unique
public SynchedPoint() { delegate_ = new
BarePoint(); }
public synchronized double x() { return
delegate_.x; }
public synchronized double y() { return
delegate_.y; }
public synchronized void setX(double v) {
delegate_.x = v;}
public synchronized void setY(double v) {
delegate_.y = v;}
}
Adding
guarded Methods
public
class BareCounter {
private long count_;
public
long value() { return count_; }
public
void add(long c) { count_ += c; }
public
BareCounter(long c) { count_ = c; }
}
public
class BoundedCounterVD implements BoundedCounter {
private
BareCounter delegate_; // fixed, unique
public
BoundedCounterVD() {
delegate_ = new BareCounter(MIN);
}
public
synchronized long value() {
return delegate_.value();
}
public
synchronized void inc() {
while (delegate_.value() >= MAX)
try {wait();} catch(InterruptedException
ex) {};
delegate_.add(1);
notifyAll();
}
public
synchronized void dec() {
while (delegate_.value() <= MIN)
try {wait();} catch(InterruptedException
ex) {};
delegate_.add(-1);
notifyAll();
}
}