Concurrent Collections & Maps

BlockingQueue

  • Failing with an IllegalArgumentException (add(), addFirst(), peek(), remove())
  • Failing and returning false (offer(), offerFirst(), poll(), pollFirst())
  • Blocking until the queue can accept the element (put(), putFirst(), take(), takeFirst())
private static BlockingQueue<String> queue = new ArrayBlockingQueue<>(50); // bounded in size
//private static BlockingQueue<String> queue = new LinkedBlockingQueue<>(); //unbounded size

queue.take();
queue.put(x);

Simple implementation of Blocking Queue:

public class BlockingQueue {

  private List queue = new LinkedList();
  private int  limit = 10;

  public BlockingQueue(int limit){
    this.limit = limit;
  }


  public synchronized void enqueue(Object item) throws InterruptedException  {
    while(this.queue.size() == this.limit) {
      wait();
    }
    //notifyAll() is only called from enqueue() and dequeue() if the queue size is equal to the size bounds (0 or limit)
    if(this.queue.size() == 0) {
      notifyAll();
    }
    this.queue.add(item);
  }


  public synchronized Object dequeue() throws InterruptedException{
    while(this.queue.size() == 0){
      wait();
    }
    if(this.queue.size() == this.limit){
      notifyAll();
    }

    return this.queue.remove(0);
  }

}

ConcurrentMap

atomic operations:

  • putIfAbsent(key, value)
  • computeIfAbsent(key, a -> new HashSet<>())
  • remove(key, value)
  • replace(key, value)
  • replace(key, existingValue, newValue)

ConcurrentHashMap supports very high concurrency, for reduce, search operations.

ConcurrentHashMap<Actor, Set<Movie>> map = new ConcurrentHashMap<>();

MovieReader reader = new MovieReader();
reader.addActorsToMap(map);
//map.computeIfAbsent(actor, a -> new HashSet<>()).add(movie);

System.out.println("# Actors = " + map.size());

int maxMoviesForOneActor = map.reduce(20, (actor, movies)->movies.size(), Integer::max);
Actor mostSeenActor = map.search(10, (actor, movies)-> movies.size()==maxMoviesForOneActor? actor:null);
System.out.println("Most seen actor = " + mostSeenActor);

int numberOfMoviesReference = map.reduce(10, (actor, movies)->movies.size(), Integer::sum);
System.out.println("Average movies per actor = " + numberOfMoviesReference/map.size());

results matching ""

    No results matching ""