【问题标题】:Finding Values with only one key in a key/value pair efficiently time-complexity wise : Java在键/值对中仅使用一个键有效地查找值 - 时间复杂性明智:Java
【发布时间】:2011-06-30 00:00:39
【问题描述】:

我希望从只有一个对应键的 Java 键/值对(具有一对多映射的映射)中检索值,而不需要遍历映射中的所有值并将其转换为 O(n) 复杂性。 Key/Value 数据结构如下:

K1 --> V1, V2
K2 --> V1、V2、V3
K3 --> V1
K4 -->
K5 --> V4、V2

如果有人对此有任何建议,或者如果可以在时间复杂性方面做得更好,将不胜感激。

【问题讨论】:

  • 您是说您有一个键/值对,其中值已知但键不知道,并且您想使用该值来查找键?
  • 第二个问题:“只有一个对应的key”是否意味着这个Map结构保证key和value之间是1对1的映射?也就是说,与地图中的所有其他值相比,每个值都是唯一的?
  • 来自TreeMapcontainsValue 的文档:This operation will probably require time linear in the map size for most implementations. 所以它假设线性只是为了首先找出地图是否甚至包含该值,别管其他保证或返回密钥。
  • @Loduwijk:键和值都是已知的。它是一对多映射。已更新帖子。 @Gnon:它会试图找到一种获得结果的最佳方法。

标签: java algorithm data-structures map time-complexity


【解决方案1】:

在 google 的 guava 中有一个非常不错的 BiMap 类,您可以在其中查找键和值(它由两个 Map 支持)。

http://code.google.com/p/guava-libraries/

已编辑:经过澄清。我认为我的答案没有太大变化。 Guava 也有非常好的 MultiMap 接口(以及它的几个实现),您很可能可以将其用于您的目的。

【讨论】:

  • @Jarek:MultiMap 是否比 O(n) 做得更好,或者换句话说,对于所有唯一值,是否只有一个与之关联的键。
  • 您可以使用“反向 MultiMap”。您不仅可以拥有多映射键-> 值,还可以并行构建另一个值-> 键。一种“BiMultiMap”(但我认为这种结构在番石榴中并不容易获得,您必须通过自己的包装器更新两个地图(但使用现有的番石榴的多重地图,代码将非常简单)。
  • 当然。但是创建结构是一回事,寻找它是另一回事。如果您有一次(或很少)创建结构并多次(或非常频繁)搜索它的情况,这种方法非常有效(相当于构建缓存)。
  • 如果你需要构建这样的结构,它至少总是 o(n) (你需要读取 n 个值)......所以我真的没有看到问题。
  • 这使得它至少是 O(n)。你不能做得比这更好。 O(n) + O(n) = O(n)
【解决方案2】:

鉴于我在 cmets 中的上述假设,快速想到的最直接的方法是拥有两个结构。两个映射,其中一个中的键是另一个中的值,反之亦然,或者有两个排序列表,您可以对其中一个执行二进制搜索,并且您找到的结果具有对姐妹元素的引用另一个清单;这会给你 o(log(n))。

如果你使用上面提到的两个镜像映射,如果它们都是HashMaps,你可以有 o(1)。你可以有一个 HashMap 和一个 HashMap,然后有一个结构来封装保持它们的同步。

【讨论】:

  • 首先,创建另一个结构会增加时间复杂度。已经发生了一个 O(n) 操作,它遍历所有键一次并创建 Map。
  • 并非如此。正如 Jarek 在上面向您指出的那样,o(n)+o(n)=o(n)。它仍然是线性时间。然而,实际上,首先创建该结构的时间大约会增加一倍。
【解决方案3】:

能否更具体一点?
哪些属性描述了您的键和值? 假设您的键是唯一的,您可以使用 LinkedList 或 ArrayList 将多个值映射到一个键。要检索所有值,您只需要引用特定的数据结构,但在某一点或另一点,您肯定需要遍历列表,所以,是的,如果您想检查每个元素,这将花费 O(n) 时间某物。另一方面,您可以将二叉树或红黑树(或其他东西)用于您的值,从而使在它们之间的搜索更加高效(正如我所说,这些取决于您的值的属性)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2015-09-28
    • 1970-01-01
    • 2019-03-03
    • 2018-10-03
    • 1970-01-01
    • 2018-06-27
    • 1970-01-01
    • 2021-12-05
    相关资源
    最近更新 更多