(C#)使Dictionary <readerwriterlockslim>成为可能的自动GC

时间:2016-03-31 10:04:07

标签: c# thread-safety readerwriterlockslim readerwriterlock

我为资源访问维护了一个ReaderWriterLockSlim对象的字典:(示例代码很难看,只是让你了解我的目的)

static ConcurrentDictionary<string, ReaderWriterLockSlim> rwResourceLocks =
                                new ConcurrentDictionary<string, ReaderWriterLockSlim>();

并像这样使用:

if (ResourceStore.Exist("resourceID")) {
    if (rwResourceLocks["resourceID"] == null) {
        /* create a new lock in thread-safe way */
    }
    rwResourceLocks["resourceID"].EnderReadLock();
    var rc = ResourceStore.GetResource("resourceID");
    /* further use of rc... */
    rwResourceLocks["resourceID"].ExitReadLock();    
}

可以动态添加或删除资源,并且它们的生命周期是不可预测的(无法监视资源的移除),随着资源量的增长,rwResourceLocks的大小也在增加,这将导致内存故障。有没有办法解决这个问题? (显然我不能简单地调用rwResourceLocks.Clear()来执行此操作)

我知道这有点复杂:(

1 个答案:

答案 0 :(得分:2)

您可以尝试使用ConditionalWeakTable代替ConcurrentDictionary。当垃圾收集器收集了密钥时,ConditionalWeakTable会自动从字典中删除一个值。

ConditionalWeakTable<object, ReaderWriterLockSlim> _locks;

if (ResourceStore.Exists("resourceID")) {
    var rc = ResourceStore.GetResource("resourceID");
    var lck = _locks.GetValue(rc, () => new ReaderWriterLockSlim());

    lck.EnterReadLock();

    // Use the resource here

    lck.ExitReadLock();
}