【问题标题】:Insert, find-min(key) and delete(based on value) functionality in logN with STL containers?使用 STL 容器在 logN 中插入、查找最小(键)和删除(基于值)功能?
【发布时间】:2012-04-10 16:44:10
【问题描述】:

这是一个有趣的问题: 假设我们有一个集合A,其中允许以下内容:

  • 插入 x
  • 查找最小 x
  • 删除A中第n个插入的元素

创建一个数据结构以允许这些在对数时间内。

最常见的解决方案是使用堆。 AFAIK,带有减少键的堆(基于一个值 - 通常是添加元素时的索引)保留一个带有 Pos[1...N] 的表,这意味着 i-th 附加值现在在索引 Pos[i] 上,所以它可以在 O(1) 中找到减少的关键。有人可以确认吗?

另一个问题是我们如何解决 STL 容器的问题?即setsmapspriority queues。我发现的一个部分解决方案是有一个带有索引的优先级队列,但按这些索引的值排序。 IE。 A[1..N] 是我们按插入顺序添加的元素。 pri-queue1..N 基于 (A[i],A[j]) 的比较。现在我们保留一个包含已删除索引的表,并验证最小值索引是否已删除。不幸的是,Find-min 与 no 稍微成正比。删除的值。 有什么替代的想法吗?

现在我想如何制定一个更普遍的问题。 使用 <key, value> 元素创建类似于 multimap 的数据结构。 Keys are not unique. Values are. 插入、查找(基于键)、查找(基于值)、删除(基于键)和删除(基于值)必须允许 O(logN)。

可能有点奇怪,这可以通过手动实现的二叉搜索树进行修改:对于每个节点操作,哈希表或基于值的映射都会使用指向节点的新指针进行更新。

类似于有一个严格排序的std::set(如果相等的键按值排序)和一个哈希表,将迭代器提供给包含该值的元素。

可以使用std::setChong Luo 描述的(std::map/hash table)。

【问题讨论】:

  • Delete the n-th inserted element in A 是什么意思。是元素排序顺序中的第 n 个元素,还是只是在有 n-1 个元素时插入的元素?
  • 有n-1个元素时插入的元素。
  • 当前std:: 容器/算法集不包括您描述的“索引”堆数据结构。这样的数据结构可以用作具有动态减少键、删除等的高效优先级队列。可以使用“索引”std::set 来实现类似的结果,尽管效率不高 - 这里讨论了这两个选项:@ 987654322@
  • 是的,这就是我正在寻找的答案。谢谢!

标签: c++ algorithm memory-management stl heap


【解决方案1】:

您可以使用两个容器的组合来解决您的问题 - 在其中添加每个连续元素和集合的向量:

  • 你使用 set 来执行 find_min 而
  • 当您插入一个元素时,您在向量中执行 push_back 并插入到集合中
  • 当您删除第 n 个元素时,您会在向量中看到它的值并将其从集合中删除。这里我假设执行删除第 n 个元素后元素的数量没有改变。

我认为你不能只用一个来自 STL 的容器来解决问题。但是有一些数据结构可以解决您的问题:

Skip list - 可以在恒定时间内找到最小值,并以平摊复杂度 O(log(n)) 执行其他两个操作。实现起来相对容易。

Tiered vector 很容易实现,find_min 会在恒定时间内执行,另外两个操作在 O(sqrt(n)) 中完成

当然还有您建议的方法 - 编写您自己的堆来跟踪其中的第 n 个元素在哪里。

【讨论】:

    猜你喜欢
    • 2014-10-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-06-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多