【问题标题】:Adjacency of intersected sets相交集的邻接
【发布时间】:2015-01-09 20:27:13
【问题描述】:

给定已知数量的 N 组项目。每个集合恰好包含 D - 1 (N >= D) 个唯一(在集合内)项目。但是 D - 1 个集合之间共享的每个项目。因此,每个集合都有两个“相邻”集合:两个相邻集合仅相差一个元素。此外,每个集合都有(如果 D 足够大)两个更远的相邻集合,它们恰好相差两个元素,等等。所有集合一起形成一个闭合链。

例如有十个元素a x b n q p j t r c。 D = 4。并且集合是(括号中是相邻集合可能排序的提示):

c x j (1)
p j x (2)
x a p (3)
p a n (4)
n q b (6)
a n q (5)
b r t (8)
b q t (7)
j c r (0)
c t r (9)

=> 相应的项目链是:r c j x p a n q b t。 向后替换的结果生成的示例。但是如何在算法上执行邻域的恢复?

One way is obvious: 简单地枚举所有可能的集合对并比较每一对的集合,无论它们是否完全不同一个元素(也可能有小的优化,但它们并不重要)。

Another way to solve the problem 是为所有可能的 D - 2-有序元素集的元组生成(对于来自输入的每个集合)散列,然后找到碰撞对。有一个知识领域叫Locality-Sensitive Hashing。

在我看来,这两种方法完全相反。散列更快,但意味着调整(桶大小,选择向量元素的散列组合方式等)并且它的大多数操作都有摊销恒定时间。因此,这涉及到一些概率动作。我可以得出结论,对于某些 D 和 N,可能会遇到性能下降。

我怀疑存在一种确定性(在上述意义上)的方法来查找所有相邻(相邻)集合。

【问题讨论】:

    标签: algorithm collision-detection collision adjacency-list


    【解决方案1】:

    这是O(D*N) 解决方案。

    如果两个集合恰好有 1 个元素不同,则它们被定义为邻居。例如。 xap 和 pan。

    定义N 桶,每个桶都标有一个元素。

    1. 将每个集合的副本放在每个关联的存储桶中。例如。存储桶a 包含xap、pan 和anq。
    2. 通过选择任何存储桶来启动链,例如a。在桶中找到 3 个组成链的集合。例如。 xap,pan,anq。这些是链中的前 3 套。
    3. 根据当前链中的最后两个集合,找到最后一个集合中不在前一个集合中的元素。对于pan 和anq,这是q。转到此存储桶。
    4. 在当前桶中,找到与链中最后一个元素相邻的集合。例如。在桶q中,相邻anq的集合是nqb。将此集合添加到链中。转到上一步,直到您回到链的第一组,例如xap。

    一个轻微的优化是一旦将集合放入链中,就从存储桶中删除它们。

    【讨论】:

    • 我会努力实现的。
    • 存在问题:如何在第一步订购xap、pan 和anq。这不是零成本运营。
    • 您没有订购该存储桶中的所有套件;无论D 有多大,都只有 3 个。您应该可以在O(D*D) 步骤中使用您在问题中描述为“明显”方法的方法执行此操作,但仅限于此存储桶。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-07-23
    • 1970-01-01
    • 2023-04-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多