July 27, 2016
The Signal idiom consists of a volatile field and at least on thread reading and one thread writing this field. The field must never be read and written in the same thread.
public class WorkerThread extends Thread { public volatile boolean canceled; public void run() { while( ! canceled ) { // do some work } } }
The Snapshot idiom consists of a class holding the current snapshot. A thread reading values gets the current snapshot and reads values from this snapshot. A thread writing values clones the current snapshot, changes this copy and set the clone as new current snapshot.
public class CopyOnWriteArrayList { final transient ReentrantLock lock = new ReentrantLock(); // usa a volatile field for the snapshot reference private transient volatile Object[] array; final Object[] getArray() { return array; } final void setArray(Object[] a) { array = a; } public boolean add(E e) { final ReentrantLock lock = this.lock; lock.lock(); try { Object[] elements = getArray(); int len = elements.length; // clone the object Object[] newElements = Arrays.copyOf(elements, len + 1); // change the local copy newElements[len] = e; // set the copy as new snapshot setArray(newElements); return true; } finally { lock.unlock(); } } public void forEach(Consumer action) { if (action == null) throw new NullPointerException(); // work with the current snapshot Object[] elements = getArray(); int len = elements.length; for (int i = 0; i < len; ++i) { @SuppressWarnings("unchecked") // all read operations are done on this snapshot E e = (E) elements[i]; action.accept(e); } } }Taken from java.util.concurrent.CopyOnWriteArrayList. Comments are mine.
A thread tries to get a value for a key calling get on a concurrent map. If the “get” method returns null it creates the missing value and calls putIfAbsent.
public Set getLanguageTagSet(String category) { // get the value Set tagset = langtagSets.get(category); // if value is null create one if (tagset == null) { tagset = createLanguageTagSet(category); // call putIfAbsent Set ts = langtagSets.putIfAbsent(category, tagset); // if putIfAbsent returns a value a other thread has created a new value in between if (ts != null) { tagset = ts; } } return tagset; }Taken from sun.util.locale.provider.JRELocaleProviderAdapter. Comments are mine.
© 2020 vmlens Legal Notice Privacy Policy