指向Java LinkedList节点的指针

时间:2014-01-22 21:22:46

标签: java performance pointers linked-list

我在O(1)处将n个条目推送到Java LinkedList 我希望稍后在O(1)删除几个独特的项目 我想保留一个带有“指针”的数组到LinkedList的唯一节点,所以我可以稍后删除它们。
有没有办法在LinkedList或任何其他java类上执行此操作? 我尝试将迭代器存储到项目中。所以我可以使用iter.remove()。但我明白当时列表中只能有一个迭代器。

我知道一个简单的解决方案可能是我自己实现链接列表。 但我宁愿使用LinkedList或已经实现的其他Java类。

2 个答案:

答案 0 :(得分:5)

Java List实现在remove *上不提供O(1)性能。使用迭代器,你必须遍历索引(O(n)),ArrayList你有一个删除后的移位(O(n)),即使LinkedList是双重的 - 链表,它不公开列表中的节点,只需重新分配下一个/最后一个引用即可直接删除它们 - 需要遍历才能找到要删除的节点(O(n))。

您可以编写自己的MyDoublyLinkedList<MyNode<T>>这样做,暴露节点而不是其中包含的值,如果您保留对节点的引用,则允许O(1)删除。索引当然是O(n)从索引列表中获取内容。根据您的使用模式,它可能是一个可行的设计选择。

如果您想使用Java提供的数据结构,请使用提供该性能的数据结构:

如果排序不重要并且没有重复项目,请使用HashSet(请注意,这不允许直接建立索引)

否则,重新编写代码以使用Map实现可能是您最好的选择。

[*] LinkedListDeque实现是O(1)用于删除头/尾。

编辑以添加评论:

如上所述,不,没有O(1)时间复杂度删除操作。

原因是这样的,除了在最极端的边缘情况下,它是无关紧要的。

在我5岁的3Ghz桌面上,LinkedList上最坏情况下的O(n)移除需要.2ms(第二点),通过索引获得100,000个条目(也就是说,索引) =长度/ 2)

我开始运行Windows交换磁盘I / O,因为这个盒子上的Windows内存管理,如果我把它增加到1,000,000个条目。

简而言之,您正在尝试解决大多数情况下不存在的问题。这通常被称为“过早优化”

答案 1 :(得分:-2)

存储指向您要删除的项目的指针的问题是,从链接列表中删除项目需要知道您要删除的项目之前的项目。

LinkedList不是为低成本删除特定项而设计的 - 您应该重新评估您使用的List(在O(1)中删除ArrayList)。你有什么理由想要一个LinkedList吗?