Clojure有一个功能sorted-set
它创建一个PersistentTreeSet
对象。顾名思义,sorted-set
创建一个排序的唯一对象集合。排序集的目的是什么?
何时排序设置有用吗?什么时候使用sorted-set
比sort
和distinct
更好?
=> (apply sorted-set [2 2 1 1 3 3])
#{1 2 3}
=> (sort (distinct [2 2 1 1 3 3]))
(1 2 3)
Clojure有一个功能sorted-set
它创建一个PersistentTreeSet
对象。顾名思义,sorted-set
创建一个排序的唯一对象集合。排序集的目的是什么?
何时排序设置有用吗?什么时候使用sorted-set
比sort
和distinct
更好?
=> (apply sorted-set [2 2 1 1 3 3])
#{1 2 3}
=> (sort (distinct [2 2 1 1 3 3]))
(1 2 3)
排序集合是有用的。对于内置的有序集合(和地图),可以在整个集合(seq
,rseq
)和两个键之间的任意“子范围”(subseq
,rsubseq
)(包含或独占)之间进行有序遍历。
如果您愿意接触核心外收藏,Contrib图书馆data.avl(其中我是作者和维护者)提供了具有附加功能的排序集和地图的风格 - nth
用于访问集排序元素,rank-of
用于发现集合中元素的排名,最近邻居查询以及返回输入集合的完整功能子集的“子范围”和分裂式操作(想想subseq
返回完全功能子集原始的,而不仅仅是一个seq,没有坚持GC中没有的子集中的任何元素)。所有这些操作在O(log n)时间最差的情况下,就像标准的排序集操作一样。
如果您只需要contains?
+ conj
+ disj
,您可能需要使用散列集,因为它们倾向于为这些操作提供更好的性能。然而,值得注意的是,如果您预计会将可能是恶意的外部源的输入添加到您的集合中,那么即使您不关心订单,也可能想要使用排序的集合。这是因为散列集的性能在存在散列冲突的情况下会降低到O(n)(对手可能会强制执行,所使用的散列函数是确定性的并且是事先确定的),而排序集O(log n)是很难保证。
如果您只需要对输入集合进行一次排序,然后重复遍历整个或各种前缀/后缀,然后构建一个排序的独特项目向量可能确实是更好的选择。甲排序集合可以仍然是优选的,即使是仅遍历-工作量,不过,如果需要在收集的任意元素开始((subseq a-set >= 5)
= SEQ超过其是> = 5相对于的a-set
那些元件的subseq
/rsubseq
特征到a-set
的排序)。
神圣的莫利,你知道很多关于套!非常感谢。 – Zaz
就个人而言,我使用的有序集合,如果我想不重复的有序数据结构,正如我在添加元素。话虽这么说,我开始与空集,而不是将其应用到列表中。
我将使用排序和独特的时间是如果我有任何其他数据结构像列表,我想要排序和删除重复。
基本上,应用一个集合给你一个新的对象与独特的元素,同时不同行为在同一个列表引用。
'distinct'返回一个新的对象(一个懒惰序列) - 就像新的和不可改变的通过施加'分拣set'返回的一个。 – Thumbnail
@Thumbnail - 谢谢你回来告诉我我错了。我接受我不知道Closure的内部工作原理。欢迎您提供您自己的答案。 –
有序集合与调用sort
和distinct
的结果之间的差异是结果类型是一个集合。
这给你为O(log n)性能(认为二进制搜索),以检查一个元素是否在集合中(contains?
)或添加一个(conj
),而一个列表,通过sort
返回和distinct
你”上d得到更糟的特性,以默认实现相同的行为。快速contains?
,conj
和disj
(=元件清除),如由Leon解释 - - 和遍历在良好定义的顺序,当你需要一套语义
你要问关于特别是“排序”位或为这台左右,一般? – cfrick
@cfrick:我想知道你什么时候想要结合这两者。 – Zaz