75-62 Técnicas de Programación Concurrentes II Lic. Ing. Osvaldo Clúa 2014 Facultad de Ingeniería Universidad de Buenos Aires Otras Otras formas formas de de Sincronización Sincronización en en Java Java java.util.concurrent Class Exchanger<V> Es una forma bidireccional de SynchronousQueue. Exchanger() V exchange(V x) V exchange(V x, long timeout, TimeUnit unit) Piedra-Tijera-Papel Resolver para dos participantes usando el Exchanger FIUBA 2014 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 2 java.util.concurrent Class Semaphore Semáforos contadores con “permits”. Semaphore(int permits) Semaphore(int permits, boolean fair) void void void void acquire() acquire(int permits) acquireUninterruptibly() acquireUninterruptibly(int permits) void release() void release(int permits) boolean tryAcquire() boolean tryAcquire(int permits) boolean tryAcquire(int permits, long timeout, TimeUnit unit) boolean tryAcquire(long timeout, TimeUnit unit) FIUBA 2014 Guardería En una guardería debe haber un adulto cada tres bebés. Programarla solo con semáforos. int availablePermits() int drainPermits() protected Collection<Thread> getQueuedThreads() int getQueueLength() boolean hasQueuedThreads() boolean isFair() protected void reducePermits(int reduction) 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 3 java.util.concurrent Class CountDownLatch Un contador bloqueante que libera al llegar a cero CountDownLatch(int count) void await() boolean await(long timeout, TimeUnit unit) void countDown() long getCount() FIUBA 2014 Prod2-Cons1 Usarla para resolver: Hay 2 productores, cada uno de ellos produce la mitad de un ítem. Un consumidor consume ambas mitades. Recién cuando ambas mitades estén consumidas puede reiniciarse el ciclo. 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 4 Java.util.concurrent Class CyclicBarrier Permite establecer un punto de encuentro entre varios threads. CyclicBarrier(int parties) CyclicBarrier(int parties, Runnable barrierAction) int await() int await(long timeout, TimeUnit unit) int getNumberWaiting() int getParties() boolean isBroken() void reset() FIUBA 2014 Sort-Merge Usarla para resolver: cada thread ordena una cantidad de Integer y pone los resultados en una cola. Cuando todos terminan se lanza una thread que hace el Merge. 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 5 Concurrencia en java.lang Class Object Cada objeto tiene un Monitor. Se espera por él con wait() Se lo libera con notify() o notifyAll() Sólo el thread que “tiene” el monitor puede ejecutar un bloque o método calificado como synchronized. Las primitivas de sincronización anteriores son independientes del Monitor. Esto puede llevar a deadlocks FIUBA 2014 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 6 Un Buffer que se bloquea (error) public class BufBloq { Semaphore lleno; Semaphore vacio; Integer item; public BufBloq() { lleno=new Semaphore (0,true); vacio=new Semaphore (1,true); } public synchronized void poner (Integer n){ try { vacio.acquire(); } catch (InterruptedException ex) { ex.printStackTrace(); } item=new Integer (n); lleno.release(); } ProdCons-WF Reescribir el Productor Consumidor usando solamente wait-notify. Use un Bufffer de 5 posiciones, N productores y K consumidores. public synchronized Integer sacar(){ try { lleno.acquire(); } catch (InterruptedException ex) { ex.printStackTrace(); } Integer n=new Integer (item); vacio.release(); return n; } } FIUBA 2014 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 7 java.util.concurrent.locks Interface Condition Factorea el wait() de Object. void await() boolean await(long time, TimeUnit unit) long awaitNanos(long nanosTimeout) void awaitUninterruptibly() boolean awaitUntil(Date deadline) void signal() void signalAll() java.util.concurrent.locks Interface Lock Soportan múltiples Condition FIUBA 2014 void lock() void lockInterruptibly() Condition newCondition() boolean tryLock() boolean tryLock(long time, TimeUnit unit) void unlock() 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 8 java.util.concurrent.locks Class ReentrantLock Mas flexibilidad que los Monitores de Object ReentrantLock() ReentrantLock(boolean fair) int getHoldCount() protected Thread getOwner() protected Collection<Thread> getQueuedThreads() int getQueueLength() protected Collection<Thread> getWaitingThreads(Condition condition) int getWaitQueueLength(Condition condition) FIUBA 2014 boolean hasQueuedThread(Thread thread) boolean hasQueuedThreads() boolean hasWaiters(Condition condition) boolean isFair() boolean isHeldByCurrentThread() boolean isLocked() void lock() void lockInterruptibly() Condition newCondition() String toString() boolean tryLock() boolean tryLock(long timeout, TimeUnit unit) void unlock() 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 9 java.util.concurrent.locks Interface ReadWriteLock Lock readLock() Lock writeLock() java.util.concurrent.locks Class ReentrantReadWriteLock Tiene dos clases internas static class ReentrantReadWriteLock.ReadLock Devuelta por readLock(). static class ReentrantReadWriteLock.WriteLock Devuelta por writeLock(). FIUBA 2014 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 10 java.util.concurrent.locks Class ReentrantReadWriteLock ReentrantReadWriteLock() ReentrantReadWriteLock(boolean fair) protected Thread getOwner() getQueuedReaderThreads() protected Collection<Thread> getQueuedThreads() protected Collection<Thread> getQueuedWriterThreads() int getQueueLength() int getReadHoldCount() int getReadLockCount() protected Collection<Thread> FIUBA 2014 getWaitingThreads(Condition condition) int getWaitQueueLength(Condition condition) int getWriteHoldCount() boolean hasQueuedThread(Thread thread) boolean hasQueuedThreads() boolean hasWaiters(Condition condition) boolean isFair() boolean isWriteLocked() boolean isWriteLockedByCurrentThread() ReentrantReadWriteLock.ReadLock readLock() ReentrantReadWriteLock.WriteLock writeLock() 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 11 Proyecto con Locks Lectores-Escritores-Plus Resolver el problema de los Lectores y Escritores. Pero, además de la solución automática, se debe poder elegir cuál de los procesos en espera es el próximo a ser atendido. FIUBA 2014 75-08 Sistemas Operativos Prof. Lic. Ing. Osvaldo Clúa 12