寻找一个算法/类计数IP地址(直方图)

Looking for an algorithm/class for counting IP addresses (histogram)

本文关键字:IP 地址 直方图 算法 一个 寻找      更新时间:2023-10-16

我需要一个简单的类来计算来自网络监控系统的IP地址的分布(直方图)。可能有1到10个10个数据包,有1到2个32个地址(或者更多,如果我们有IPv6接口)。我理想中寻找的是一个c++类,它将自动创建直方图,然后,当达到限制时,开始通过某种前缀路由组合不太受欢迎的节点。

有人知道这样的东西吗,或者我需要写出来吗?

谢谢!

您所描述的内容听起来像是Count-Min sketch数据结构的完美用例。此数据结构用于近似数据流中各种元素的频率,并且可以调优以精确地使用一定数量的内存。此外,给定固定的内存限制,您可以调整它的准确性以及与您希望的确切答案的接近程度。我的理解是,Google使用这种数据结构来识别频繁的搜索,而不必使用大量的磁盘空间。

作为附加的优点,数据结构永远不会低估给定值的真实频率。也就是说,如果你想查询你看到一个给定IP地址的频率,Count-Min草图将总是给你一个不小于真实数字的值。

Count-Min草图非常容易实现——你只需要一堆不同的哈希函数和一个2D数组。您还可以在Google的数据结构页面上找到Count-Min草图的各种不同实现。

希望这对你有帮助!

+1到@templatetypedef,求近似解

为了完整性,如果需要存储精确的计数,就没有办法存储精确的数字。然而,根据您的需求,您可能能够显著减少所需的空间(例如,10.*.*.)。*和192.68.*。* ip永远不能被公开路由;还有很多其他的,比如25.*.*。*,目前没有被公开路由)。您还可以(同样取决于您的需求)能够将大组不重要的ip集合在一起。

如果您可以将空间需求降低到足够低的程度,您可以使用bitset尽可能紧凑地将计数存储在内存中。如果没有简单的方法将ip-address映射到bitset-address,则需要使用类似简洁尝试的方法来映射它们。一个简洁的树将需要一个字节(平摊)每个ip-group。

并且,如果不能将其降低到足够低的程度,则可能需要使用数据库,并接受性能损失。

您可以看看边界网关协议(BGP)或GRiDA算法。

我已经开发了一个算法来解决这个问题。该算法以基数树/前缀树的形式存储IP地址计数。每个节点记录地址的下一位,如果是终端节点则记录计数。如果节点太多,则从树的范围开始组合节点;首先组合具有最低计数的叶子的节点。

它非常优雅,非常快。如果有兴趣的话,我可以把c++代码贴出来。