Разработка блокировки на основе ключа (или карты блокировки )

Я пытаюсь разработать средство блокировки на основе ключа: что-то вроде обычной повторной блокировки, но вместо lock () и unlock () вы блокируете (ключ) и разблокируете (key), с контрактом, что никто не сможет заблокировать (key1) одновременно, если key.equals (key1).

Будет ли работать этот код? Есть ли более эффективные решения? Мне особенно не нравится цикл while при попытке установить блокировку на карту ...

package luca;

import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.locks.ReentrantLock;

public class KeyedReentrantLock<K> {
    private ConcurrentMap<K, ReentrantLock> lockMap = new ConcurrentHashMap<K, ReentrantLock>();

    public void lock(K key) {
        ReentrantLock oldLock = lockMap.get(key);
        if (oldLock != null && oldLock.isHeldByCurrentThread()){
            // increase lock count and return.
            oldLock.lock();
            return;
        }
        ReentrantLock newLock = new ReentrantLock();
        newLock.lock();
        while ((oldLock = lockMap.putIfAbsent(key, newLock)) != null){
            // wait for the old lock to be released;
            oldLock.lock();
            oldLock.unlock();
        }
        return;
    }

    public void unlock(K key){
        ReentrantLock lock = lockMap.get(key);
        if (lock == null) throw new IllegalMonitorStateException("There was no lock for this key!");
        if (lock.getHoldCount() == 1){
            lockMap.remove(key);
        }
        lock.unlock();
    }

}
14
задан lultimouomo 2 December 2011 в 10:13
поделиться