随机访问链表的数据结构

时间:2015-05-20 12:21:35

标签: java data-structures

我需要一个数据结构,它能够为给定的int提供前后邻居,这是结构的一部分。

我为自己设定的一些标准:

  • 写一次,多次阅读
  • 包含100到1000 int
  • 高效:数量级O(1)
  • 具有内存效率(理想情况下,整数的大小+一些内务比特)
  • 用纯Java实现(没有这个库,我想学习)
  • 项目是唯一的
  • 没有并发要求
  • int是从外部排序的,该顺序很可能不是自然顺序,并且必须保留该顺序(即,没有任何关于两个相邻整数之间的价值差异的合约 - 任何int可能更大或更小比它在顺序中的int)。

这是在Java中,并且主要是理论上的,因为我已经开始使用下面描述的解决方案。

我考虑过的事情:

  • LinkedHashSet :非常快速地找到一个项目,O(1)的顺序,并且非常快速地检索下一个邻居。没有明显的方法来获得前一个邻居没有反向排序集。仅限盒装整数对象。
  • int [] :内存非常简单,因为不需要装箱,非常快速地获取上一个和下一个邻居,项目的检索是O(n),因为索引未知且数组遍历是必需的,这是不可接受的。

我现在使用的是 int []和HashMap的组合

  • HashMap,用于检索int []
  • 中特定int的索引
  • int []用于检索该int的邻居

我喜欢什么:

  • 邻居查找理想情况下是O(2)
  • int []不做拳击
  • 表现理论上非常好

我不喜欢:

  • HashMap进行两次拳击(键和值)
  • 整数被存储两次(在地图和数组中)
  • 理论内存使用可以改进很多

我很想知道更好的解决方案。

2 个答案:

答案 0 :(得分:1)

一种解决方案是在添加元素时对数组进行排序。这样,前一个元素始终为i-1并且为了找到一个值,您可以使用二进制搜索,即O(log(N))。

下一个明显的候选人是balanced binary tree。对于这种结构,insert有点贵,但查找又是O(log(N))。

如果值不是32位,那么您可以通过使用第二个数组来使查找更快,其中每个值都是第一个中的索引,索引是您要查找的值。

更多选项:您可以查看位集,但这又取决于值可以具有的范围。

Commons Lang有一个哈希映射,它使用原始int作为键:http://grepcode.com/file/repo1.maven.org/maven2/commons-lang/commons-lang/2.6/org/apache/commons/lang/IntHashMap.java 但是类型是内部的,所以你必须复制代码才能使用它。

这意味着你不需要自动装箱任何东西(拆箱很便宜)。

相关:

答案 1 :(得分:0)

  

整数在外部排序,该顺序很可能不是自然顺序,并且必须保留该顺序(即,没有任何关于两个相邻整数之间的价值差异的合约)。

这说" Tree"对我来说。就像Aaron所说的那样,昂贵的插入但有效的查找,如果你曾经写过一次就是你想要的,阅读很多。

编辑:考虑一下这个,如果一个值只能有一个孩子和一个父母,并且给出了所有其他要求,我认为ArrayList可以正常工作。它简单而且非常快,即使它是O(n)。但是如果数据集增长,那么使用Map-List组合可能会更好。

在使用这些结构时请记住,O()方面的理论性能并不总是与真实字性能相对应。您需要考虑数据集大小和整体环境。一个例子:ArrayList和HashMap。理论上,List是O(n)用于未排序查找,而Map是O(1)。但是,在创建和管理地图条目时会产生很多开销,实际上在较小的集合上会比List更差。

既然你说你不必担心记忆,我就会远离array。管理大小的复杂性在您指定的数据集大小上是不值得的。