按Value排序ConcurrentDictionary

时间:2011-12-22 19:25:11

标签: c# c#-4.0 concurrency parallel-processing concurrent-programming

我可以按如下方式对ConcurrentDictionary进行排序:

static ConcurrentDictionary<string, Proxy> Proxies = 
    new ConcurrentDictionary<string, Proxy>();

Proxies.OrderBy(p => p.Value.Speed);

哪个好,除了我想将新的重新排序列表设置为字典,有效地对字典本身进行排序,而不是仅仅接收已排序项的结果列表。

我尝试做这样的事情,但没有运气 - 字典仍然无序后:

Proxies = new ConcurrentDictionary<string,Proxy>(
    Proxies.OrderBy(p => p.Value.Speed));

这似乎对字典没有影响。我也尝试将OrderBy结果转换为一个新的var,认为它可能对委托产生影响但仍然没有运气。

如何重新订购此ConcurrentDictionary,然后强制字典成为OrderBy的重新排序结果?

5 个答案:

答案 0 :(得分:9)

简单字典不是已排序的集合。它们只是将键映射到值的集合。 ConcurrentDictionary也不例外。

您需要SortedConcurrentDictionary(类似于SortedDictionary),但此数据结构不存在。

至于你是否真的需要一个有序的“字典”,我们需要了解更多关于你的用例的信息。这是一个虚假的优先队列吗?您可以简单地使用ConcurrentBag<Proxy>并在事后执行排序吗?

如果你需要采用集合,并且在下游并行方法中按排序顺序使用代理,我建议看一下创建custom Partitioner,可能借用MSDN example of an OrderablePartitioner

答案 1 :(得分:2)

字典,尤其是ConcurrentDictionary,基本上没有排序。

如果您需要已排序的集合,则需要将值存储为其他类型,例如SortedDictionary<T,U>

答案 2 :(得分:2)

解决方案是使用SortedSet<T>,经过数小时的研究和代码修订后发现。排序集提供DictionaryHashSet的唯一性,但也允许排序 - DictionaryHashSet都不允许排序。

答案 3 :(得分:2)

如果你经常在一个不可变的类中调用它,可能效率不高,但很简单:

Imports System.Collections.Concurrent

Public Class SortedConcurrentDictionary(Of TKey, Tvalue)
Inherits ConcurrentDictionary(Of TKey, Tvalue)

    Shadows ReadOnly Property Values As IEnumerable(Of Tvalue)
        Get
            If MyBase.Values.Count = 0 Then
                Return MyBase.Values
            End If
            Return From k In Keys Order By k Select Me(k)
        End Get
    End Property
End Class

答案 4 :(得分:0)

ConcurrentDictionary,就像Dictionary一样,不知道排序的概念,即它不包含任何排序信息。 OrderBy()的结果具有特定顺序,但在分配给Proxies时,订单信息会丢失。

请注意,IDictionary的排序实施,即SortedDictionarySortedList