简体   繁体   English

如何在 Pharo 中订购字典?

[英]How is ordered a Dictionary in Pharo?

Let's say we have a loop that enters Association s to a Dictionary in a clear order:假设我们有一个循环,它以明确的顺序将Association s 输入到Dictionary中:

| d |

d := Dictionary new: 10.

1 to: 10 do: [ :i |
    d add: i -> (i + 9 printStringBase: 20)
].

d

When I evaluate this code I get a Dictionary in a "twisted" order:当我评估这段代码时,我得到一个“扭曲”顺序的Dictionary

9 -> I
5 -> E
1 -> A
10 ->J
6 -> F
2 -> B
7 -> G
3 -> C
8 -> H
4 -> D

Each time a Dictionary with the same entry data is created it have the same order, so I assume it is a feature not a bug..?每次创建具有相同条目数据的Dictionary时,它都具有相同的顺序,所以我认为这是一个功能而不是错误..?

I use Pharo v9.0.21.我使用 Pharo v9.0.21。

A Dictionary is not an ordered collection.字典不是有序集合。 Instead it is a keyed collection, keeping key-value pairs.相反,它是一个键控集合,保留键值对。

There is an OrderPreservingDictionary for you to use: https://github.com/pharo-contributions/OrderPreservingDictionary有一个 OrderPreservingDictionary 供你使用: https://github.com/pharo-contributions/OrderPreservingDictionary

In addition to this other answer is is worth explaining the apparent disorder shown in the question.除了这个其他答案值得解释问题中显示的明显混乱。

Firstly observe that Dictionary new: 10 will create a new instance of Dictionary with capacity for a prime number p of associations greater than 10 .首先观察Dictionary new: 10将创建一个新的Dictionary实例,其容量为大于10的素数p的关联。 Say 11, 13, 17, whatever.说 11、13、17,随便什么。

Secondly, for every association added, the dictionary will compute the hash value of the key and deduce the location from its remainder modulo p .其次,对于添加的每个关联,字典将计算键的 hash 值并从其余数模p推导出位置。

Since all keys occurring in the example are instances of SmallInteger , their hashes will be themselves(*).由于示例中出现的所有键都是SmallInteger的实例,因此它们的哈希值将是它们自己 (*)。 And since these are smaller than p , they will equal the modulo and hence be stored in the slots derived from their values in some implementation-dependent way.并且由于它们小于p ,它们将等于模数,因此以某种依赖于实现的方式存储在从它们的值派生的槽中。

Finally, the printing method is free to enumerate the associations in any order.最后,打印方法可以自由地以任何顺序枚举关联。


(*) While this is true in some dialects, I've checked in Pharo and this is not true, 3 hash is not 3 etc. which explains the "twisting" in the case of Pharo. (*) 虽然这在某些方言中是正确的,但我在 Pharo 中检查过这不是真的, 3 hash不是3等等,这解释了 Pharo 的“扭曲”。

For completeness of the answer there is such thing as ordered Dictnionary.为了答案的完整性,有有序的 Dictnionary 这样的东西。

At Smalltalk/X the #OrderedDictionary is defined as:Smalltalk/X中, #OrderedDictionary被定义为:

Dictionary subclass:#OrderedDictionary
        instanceVariableNames:'order'
        classVariableNames:''
        poolDictionaries:''
        category:'Collections-Sequenceable'

"/     I am a subclass of Dictionary whose elements (associations) are ordered in a
"/     similar fashion to OrderedCollection.
"/     That is, while being filled via #at:put: messages (or similar Dictionary protocol),
"/     the order in which associations are added, is remembered and accessible via the #atIndex:
"/     or #order messages. 
"/     Therefore, this combines fast access via hashing with a defined order when enumerating.
"/     
"/     [instance variables:]
"/         order <OrderedCollection>       Ordered collection of keys reflecting the order of
"/                                         associations in the dictionary.
"/ 
"/     [complexity:]
"/         access by index: O(1)
"/         access by key: O(1)
"/         searching: O(n)
"/         insertion: mostly O(1)
"/         removal: mostly O(N) (because order will have O(n) behavior)
"/         
"/     [author:]
"/         Ifor Wyn Williams 
"/         Changed by: exept

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM