zoukankan      html  css  js  c++  java
  • Finding intersection and union of two sets.

    假设集合A有n个元素,集合B有m个元素,两个集合取自某个空间(universe)。

    1.1, 首先从最naive的办法开始。对B中元素,挨个测试是不是在A中,交集、并集都是O(m*n),平方级别的算法。

    1.2, 将A先排序,O(n*logn),然后,对B中元素,挨个测试是不是在A中,这时可以二分了,O(m*logn),一共是O(n*logn)+O(m*logn)=O((m+n)*logn)。

    所以如果m<n的话,对调一下A和B比较好,也就是复杂度是O( (m+n) * log( min(m, n) ) ).

    这种思路的本质是,只利用了“A是集合”这个事实,然后对B中元素进行is in A的测试,测试过程需要O(m*logn)的复杂度。

    1.3, A、B都排序一下,剩下的工作就和merge-sort很像了,两个指针交替往前走。最坏情况下,需要max(m, n)次比较。

    对于基于sorting的办法,也许可以再优化?

    2.1,既然已经排完序了,那么立刻就知道两边元素的范围了,譬如 A in [a1, a2], B in [b1, b2],根据这个上下界,可以去掉一部分,然后对真正有overlap的部分,进行merge。极端情况下,根据上下界可以去掉绝大部分乃至全部元素。

    另一种思路,用hash-table来。

    3.1, A构造一个hash-table,O(n)的插入。然后,对B中元素,挨个测试是不是在表中。这次,连二分也不用了,O(m)的测试,一共是O(m + n)。

    代价呢?额外的hash-table,O(n)的table(根据hash-table的性质,通常还会更大)。

    其他一些思路,可能适用于某些特定场合。

    4.1, 倘若元素范围不大,可以上bitmap(本质上也是hash-table),两个集合用两个bitmap表示,交集就是and,并集就是or,太方便了。

    4.2, 另外一个可能的解决方案,bloom filter。另开博文吧,参见:http://www.cnblogs.com/qsort/archive/2011/05/06/2039223.html

  • 相关阅读:
    HeidiSQL
    PostgreSQL
    MariaDB
    NLog
    0 vs null
    忘带手机的那么一天
    江城子·己亥年戊辰月丁丑日话凄凉
    单体 VS 微服务
    java面向对象(四)之重写、重载
    java面向对象(三)之抽象类,接口,向上转型
  • 原文地址:https://www.cnblogs.com/qsort/p/2039201.html
Copyright © 2011-2022 走看看