从通用链接列表中删除所有重复项

时间:2015-12-10 07:23:16

标签: java linked-list duplicates

这是我到目前为止所获得的代码,它删除了重复项的所有第一个实例,但是如果我重复了一个元素,它将只删除第一个实例并保留其余的实例列表中的元素。

//remove all duplicate items from list.
// if list is null or empty leave it unchanged

public static <T extends Comparable<? super T>>
        void deleteReps(LinkedList<T> list)
{
   for (int i = 0; i < list.size(); i++)
    {
        T item = list.get(i);
        for(int j = i + 1; j < list.size(); j++)
        {
            if(item == null && list.get(j) == item || item != null && item.equals(list.get(j)))
            {
                list.remove(j);
            }
        }
    }
}

3 个答案:

答案 0 :(得分:1)

根据Eran的回答,我建议您使用Iterator来迭代列表,因为它不需要手动索引,并且在迭代列表时也允许删除项目。

答案 1 :(得分:0)

从列表中删除元素时,您必须记住这会减少列表中每个项目的索引以及列表的大小。

修改

正如Sharonbn所说,这是一种使用迭代器的工作方法:

File->Source-Control

这可能不是最有效的方法,因为它创建了另一个列表来比较对象,但它确实完成了工作。

答案 2 :(得分:0)

使用LinkedList,您正在处理与节点链接在一起的对象的基于引用的实现。节点包含Object和仅对下一个Node的引用。您应该尝试不使用索引迭代LinkedList,因为当您开始删除或添加节点时,索引会更改。如果删除其内容,则将空格保留为null的数组不同,一旦从LinkedList中删除节点,列表的大小就会减小,因为前一个节点现在引用了删除后的节点和删除的节点之后的节点在记忆中迷失了。因此,在您的示例中,您需要考虑在删除重复项后索引将发生更改。因此,您应该始终尝试通过引用遍历Java中的LinkedList而不是索引。在您的情况下,这可能有效:

void deleteReps(LinkedList<T> list)
{
    Node prev = head;                         // A node to traverse with starts at the head
    Node temp = head.getNext();               // A second node to traverse with
    Node current = prev;                      // The node in question

    while(prev.getNext() != null)             // While the node after prev isn't the end 
    {                                         //    of the list
        T item = current.data;                // The item we are looking for duplicates of

        while(temp != null)                   // While temp isn't at the end of the list
        {
            if(temp.data == item)             // If the item in temp is the same as the
            {                                 //    item we are looking for

                prev.setNext(temp.getNext()); // Set the next Node of prev to the node
                                              //    after temp. This "deletes" the Node
                                              //    at temp
                prev = temp;                  // prev is now temp
                temp = temp.getNext();        // temp is the next Node
            }
            else                              // Else if the item is different
            {
                prev = temp;                  // prev is now temp
                temp = temp.getNext();        // temp is now the next Node
            }
        } // end while

        current = current.getNext();          // current is now the next Node 
                                              //    so that the
                                              //    the next item we are looking for 
                                              //    duplicates of is an item still in
                                              //    the LinkedList
        prev = current;
        temp = prev.getNext();
    } // end while                               
}  

我给出了彻底的评论,因此您可以遵循此算法背后的逻辑。这会在删除节点时考虑缩小的LinkedList,因为current.getNext()将始终是删除重复后仍在LinkedList中的节点。