问题很简单:我需要找到最佳策略来实现基于Redis表示的准确HyperLogLog联合 - 这包括在导出数据结构以供其他地方使用时处理它们的稀疏/密集表示。
有两种策略,其中一种似乎非常简单。我已经看过实际的Redis源代码了,我遇到了一些麻烦(在我自己的C中并不大),从精确和高效的角度来看,使用内置的结构/例程或开发自己的内容是否更好。对于它的价值,我愿意牺牲 space 以及在某种程度上的错误(stdev + -2%)以追求效率与极大的集合。
到目前为止最简单的两个 - 基本上我只是将无损联合(PFMERGE)与此原理结合使用来计算重叠的估计。在许多情况下,测试似乎表明这种运行是可靠的,尽管我无法准确处理非常高的效率和准确性(某些情况下会产生20-40%的错误,这在这个用例中是不可接受的)。
基本上:
aCardinality + bCardinality - intersectionCardinality
或者,在多组情况下......
aCardinality + (bCardinality x cCardinality) - intersectionCardinality
似乎在许多情况下都有很好的准确性,但我不知道我是否相信它。虽然Redis有许多内置的低基数修饰符,旨在规避已知的HLL问题,但我不知道野性不准确(使用包含/排除)的问题是否仍存在于大小差异很大的情况下......
这种方式似乎更有趣,但我觉得它可能与Redis的一些现有优化计算重叠(即,我没有从头开始实现我自己的HLL算法)。
通过这种方法,我会使用MinHash算法对随机抽样的箱子(我不认为LSH实现值得麻烦)。这将是一个单独的结构,但通过使用minhash获取集合的Jaccard索引,您可以有效地将union基数乘以该索引,以获得更准确的计数。
问题是,我不太熟悉HLL,虽然我很想深入研究Google论文,但我需要在短期内实现可行的实施。有可能我忽略了Redis现有优化的一些基本考虑因素,或者算法本身,它允许计算上便宜的交叉点估计具有相当宽松的置信区间。
因此,我的问题是:
如果我愿意牺牲空间(以及小程度,精确度),如何使用redis最有效地获得N个巨大(数十亿)集的计算上便宜的交集估计? ?
答案 0 :(得分:4)
一段时间后阅读本文。可能会回答你的大部分问题。包含原则不可避免地使大量集合的误差范围复杂化。 Min-Hash方法将是最佳选择。
答案 1 :(得分:1)
第三种策略是估计任何两组的交集大小,以HyperLogLog草图给出:最大似然估计。
有关详细信息,请参阅以下文章 http://oertl.github.io/hyperloglog-sketch-estimation-paper/