Sorting Clojure中对大矢量数据进行排序的最快方法
我需要能够以这样一种方式存储来自集合的数据,即任何给定密钥集的平均值不大于特定的数字 例如,假设任何给定的3个集合的“:num”的平均值不能大于或等于10,我有以下集合:Sorting Clojure中对大矢量数据进行排序的最快方法,sorting,clojure,Sorting,Clojure,我需要能够以这样一种方式存储来自集合的数据,即任何给定密钥集的平均值不大于特定的数字 例如,假设任何给定的3个集合的“:num”的平均值不能大于或等于10,我有以下集合: (def my-set ({:num 0} {:num 0} {:num 0} {:num 5} {:num 5} {:num 5} {:num 10} {:num 10} {:num 10} )) 在此集合中,最后3个哈希不能保持彼此相
(def my-set
({:num 0}
{:num 0}
{:num 0}
{:num 5}
{:num 5}
{:num 5}
{:num 10}
{:num 10}
{:num 10}
))
在此集合中,最后3个哈希不能保持彼此相邻,因为它们的平均值为10,但可以这样重新组织集合,因为任何给定3个哈希的平均值为5:
(def my-set
({:num 0}
{:num 5}
{:num 10}
{:num 0}
{:num 5}
{:num 10}
{:num 0}
{:num 5}
{:num 10}
))
我的问题是,假设这个集合比9个条目的样本大得多,可能有数百万条,而整个集合的总平均数是5条或更少,那么什么是对这些条目进行排序的最快和最有效的方法,以使任何3条(或10条或100条,或任何给定的样本大小)的平均数永远不会达到10条
以下是我的psuedocode解决方案,我觉得太慢了:
1) 按值对集合排序:number
2) 将集合除以2,然后按该索引的编号拆分
3) 以与第二个集合相反的顺序交错第一个集合
因此,第一个集合看起来像:
({:num 0} {:num 0} {:num 0} {:num 5})
和第二次收集(反向):
使用交织,生成的集合将是:
({:num 0}{:num 10}{:num 0}{:num 10}{:num 0}{:num 10}{:num 5}{:num 5}{:num 5})
一定有更好的方法做这件事。这里有一种方法:
(def data-9
[{:num 0}
{:num 0}
{:num 0}
{:num 5}
{:num 5}
{:num 5}
{:num 10}
{:num 10}
{:num 10}] )
(def data-11
(into (vec data-9)
[{:num 0}
{:num 10}] ))
(defn interleave-by
[data group-size]
(let [data-num (count data)
part-size (quot data-num group-size)
leftover-num (- data-num (* part-size group-size))
data-sorted (sort-by :num data)
data-leftover (take leftover-num data-sorted)
data-use (drop leftover-num data-sorted)
data-parts (partition-all part-size data-use)
data-reordered (apply mapcat vector data-parts)
data-final (reduce into (vec data-leftover) data-reordered)
]
data-final ))
(newline)
(println (interleave-by data-9 3))
data-num =>
9
part-size =>
3
leftover-num =>
0
data-sorted =>
({:num 0}
{:num 0}
{:num 0}
{:num 5}
{:num 5}
{:num 5}
{:num 10}
{:num 10}
{:num 10})
data-leftover =>
()
data-use =>
({:num 0}
{:num 0}
{:num 0}
{:num 5}
{:num 5}
{:num 5}
{:num 10}
{:num 10}
{:num 10})
data-parts =>
(({:num 0} {:num 0} {:num 0})
({:num 5} {:num 5} {:num 5})
({:num 10} {:num 10} {:num 10}))
data-reordered =>
({:num 0}
{:num 5}
{:num 10}
{:num 0}
{:num 5}
{:num 10}
{:num 0}
{:num 5}
{:num 10})
data-final =>
[[:num 0]
[:num 5]
[:num 10]
[:num 0]
[:num 5]
[:num 10]
[:num 0]
[:num 5]
[:num 10]]
(interleave-by data-9 3) =>
[[:num 0]
[:num 5]
[:num 10]
[:num 0]
[:num 5]
[:num 10]
[:num 0]
[:num 5]
[:num 10]]
如果没有组大小的整数倍,则更困难。这会导致额外的复杂性,包括剩余数据
(newline)
(println (interleave-by data-11 3))
data-num =>
11
part-size =>
3
leftover-num =>
2
data-sorted =>
({:num 0}
{:num 0}
{:num 0}
{:num 0}
{:num 5}
{:num 5}
{:num 5}
{:num 10}
{:num 10}
{:num 10}
{:num 10})
data-leftover =>
({:num 0} {:num 0})
data-use =>
({:num 0}
{:num 0}
{:num 5}
{:num 5}
{:num 5}
{:num 10}
{:num 10}
{:num 10}
{:num 10})
data-parts =>
(({:num 0} {:num 0} {:num 5})
({:num 5} {:num 5} {:num 10})
({:num 10} {:num 10} {:num 10}))
data-reordered =>
({:num 0}
{:num 5}
{:num 10}
{:num 0}
{:num 5}
{:num 10}
{:num 5}
{:num 10}
{:num 10})
data-final =>
[{:num 0}
{:num 0}
[:num 0]
[:num 5]
[:num 10]
[:num 0]
[:num 5]
[:num 10]
[:num 5]
[:num 10]
[:num 10]]
(interleave-by data-11 3) =>
[{:num 0}
{:num 0}
[:num 0]
[:num 5]
[:num 10]
[:num 0]
[:num 5]
[:num 10]
[:num 5]
[:num 10]
[:num 10]]
- 这是关于算法的,只是顺便说一下与 克罗朱尔
- 所需要的不是这样的排序。我们正在寻找一个合适的人选 对数据进行排列,使相邻的三个(或多个)数据不存在 数字平均为5或更多。我们可以先把数字映射到 导出排列
- 不必有任何解决办法。例如,如果任何数字大于 十五,没有一个
- 这看起来类似于。很可能是这样 精确的解决方案是难以解决的,但贪婪的或其他的方法会解决这个问题 要实事求是
我建议你试着把这个问题放在电脑上 谢谢你!我刚刚意识到在我求解算法的逻辑中有一些主要的缺陷,但我相信这些信息在将来会派上用场。您可能的数值集是否受到已知项的限制?就像您的示例中的
{0510}
或者集合中可能有任意数字(我的意思是您是否有一些已知的约束,或者只是一些随机输入集合)?
(newline)
(println (interleave-by data-11 3))
data-num =>
11
part-size =>
3
leftover-num =>
2
data-sorted =>
({:num 0}
{:num 0}
{:num 0}
{:num 0}
{:num 5}
{:num 5}
{:num 5}
{:num 10}
{:num 10}
{:num 10}
{:num 10})
data-leftover =>
({:num 0} {:num 0})
data-use =>
({:num 0}
{:num 0}
{:num 5}
{:num 5}
{:num 5}
{:num 10}
{:num 10}
{:num 10}
{:num 10})
data-parts =>
(({:num 0} {:num 0} {:num 5})
({:num 5} {:num 5} {:num 10})
({:num 10} {:num 10} {:num 10}))
data-reordered =>
({:num 0}
{:num 5}
{:num 10}
{:num 0}
{:num 5}
{:num 10}
{:num 5}
{:num 10}
{:num 10})
data-final =>
[{:num 0}
{:num 0}
[:num 0]
[:num 5]
[:num 10]
[:num 0]
[:num 5]
[:num 10]
[:num 5]
[:num 10]
[:num 10]]
(interleave-by data-11 3) =>
[{:num 0}
{:num 0}
[:num 0]
[:num 5]
[:num 10]
[:num 0]
[:num 5]
[:num 10]
[:num 5]
[:num 10]
[:num 10]]