可以在C#中创建一个真正弱键字典吗? [英] Is it possible to create a truely weak-keyed dictionary in C#?
问题描述
我正在努力弄清楚C#的真实 WeakKeyedDictionary<,>
的细节,但我遇到困难。
I'm trying to nut out the details for a true WeakKeyedDictionary<,>
for C#... but I'm running into difficulties.
我意识到这是一个不平凡的任务,但似乎无法声明一个 WeakKeyedKeyValuePair<,>
(其中GC
I realise this is a non-trivial task, but the seeming inability to declare a WeakKeyedKeyValuePair<,>
(where the GC only follows the value reference if the key is reachable) makes it seemingly impossible.
有两个主要问题我看到:
There are two main problems I see:
-
我迄今为止看到的每个实现都不会在收集密钥后修剪值。想想这个 - 使用这样一个字典的主要原因之一是防止这些值被保留(不仅仅是键!),因为它们是不可达到的,但是在这里它们被强引用所指向。
Every implementation I've so far seen does not trim values after keys have been collected. Think about that - one of the main reasons for using such a Dictionary is to prevent those values being kept around (not just the keys!) as they're unreachable, but here they are left pointed to by strong references.
是的,添加/删除足够的字典,最终会被替换,但是如果没有,那怎么办?
Yes, add/remove from the Dictionary enough and they'll eventually be replaced, but what if you don't?
没有一个假设的 WeakKeyedKeyValuePair<,>
(或者另一种方法,告诉GC只有当该键可达时才标记该值)引用它的任何值钥匙永远不会被收集。存储任意值时,这是一个问题。
Without a hypothetical WeakKeyedKeyValuePair<,>
(or another means of telling the GC to only mark the value if the key is reachable) any value that refers to it's key would never be collected. This is a problem when storing arbitrary values.
问题1可以以非理想/黑客方式解决:使用GC通知等待完整的GC完成,然后在另一个线程中修剪字典。这个我是半决定的。
Problem 1 could be tackled in a fairly non-ideal/hackish way : use GC Notifications to wait for a full GC to complete, and then go along and prune the dictionary in another thread. This one I'm semi-ok with.
但问题2让我陷入困境。我意识到这很容易被所以不这样做所抵制,但是我有疑问 - 这个问题是否可以解决?
But problem 2 has me stumped. I realise this is easily countered by a "so don't do that", but it has me wondering - is this problem even possible to solve?
推荐答案
看看 ConditionalWeakTable< TKey,TValue>类别。
使编译器能够将对象字段动态地附加到托管对象。
Enables compilers to dynamically attach object fields to managed objects.
它本质上是一个字典,键和值都是 WeakReference ,只要密钥存活,该值就会保持活着。
It's essentially a dictionary where both the key and the value are a WeakReference, and the value is kept alive as long as the key is alive.
注意!这个类不使用 GetHashCode
和等于
进行平等比较,它使用 ReferenceEquals
。
Note! This class does not use GetHashCode
and Equals
to do equality comparisons, it uses ReferenceEquals
.
这篇关于可以在C#中创建一个真正弱键字典吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!