给定节点如何在单链表中找到先前的节点

时间:2011-08-25 23:47:09

标签: java c list data-structures linked-list

给定当前节点,如何在单链接列表中找到其先前节点。谢谢。逻辑将做,代码表示赞赏。我们都知道给定一个根节点可以进行顺序遍历,我想知道是否有一种更智能的方法可以避免顺序访问开销。 (假设没有访问根节点)谢谢。

12 个答案:

答案 0 :(得分:6)

你不能。

根据定义,单链接列表仅将每个节点链接到其后继节点,而不是前导节点。没有关于前任的信息;甚至没有关于它是否存在的信息(你的节点可能是列表的头部)。

您可以使用双向链接列表。 您可以尝试重新排列所有内容,这样您就可以将前一个作为参数传入。

您可以扫描整个堆,查找看起来像前导节点的记录,该节点带有指向您节点的指针。 (不是一个严肃的建议。)

答案 1 :(得分:2)

从头开始遍历列表,直到遇到next链接指向您当前节点的节点。

但是如果你需要这样做,也许你不应该首先使用单链表。

答案 2 :(得分:2)

假设您正在讨论前向单链表(每个节点只有一个指向'next'的指针等),您将不得不从列表的开头迭代,直到找到“下一个”相等的节点到你当前的节点。显然,这是一个缓慢的O(n)操作。

希望这有帮助。

答案 3 :(得分:2)

单链表的唯一选择是线性搜索,如下所示(类似Python的伪代码):

find_previous_node(list, node):
   current_node = list.first
   while(current_node.next != null):
       if(current_node.next == node):
          return current_node
       else:
          current_node = current_node.next
   return null

答案 4 :(得分:2)

如果要删除当前节点,则无需删除先前的节点即可完成该操作。

Python代码:

def deleteNode(自己,节点):

node.val = node.next.val

node.next = node.next.next

@删除链接列表中的节点

答案 5 :(得分:0)

使用nodeAt()方法并传递当前节点的头部,大小和索引。

 public static Node nodeAt(Node head,int index){
    Node n=head;
    for(int i=0;i<index;i++,n=n.next)
      ;
    return n;
  }

其中n返回前一个节点。

答案 6 :(得分:0)

这是我在解决问题时发现的某种黑客攻击(删除列表中的每个偶数节点)

    internal void DeleteNode(int p)
    {
        DeleteNode(head, p);
    }

    private void DeleteNode(Node head, int p)
    {
        Node current = head;
        Node prev = null;

        while (current.next != null)
        {
            prev = current;
            current = current.next;
            if (current.data == p)
            {
                prev.next = current.next;
            }
        }
    }

现在,在prev中,您可以分配当前值,然后将当前值移动到下一个,从而prev包含上一个节点。 希望这会有所帮助...

答案 7 :(得分:0)

这是一个线性搜索的小技巧:只需传入您要搜索的上一个节点的节点或其位置:

private MyNode findNode(int pos) {
//node will have pos=pos-1
        pos-- = 1; 
        MyNode prevNode = null;
        int count = 0;  
        MyNode p = first.next;  // first = head node, find it however you want.
//this is for circular linked list, you can use first!=last for singly linked list
        while (p != first) { 
            if (count == pos) {
                prevNode = p;
                break;
            }
            p = p.next;
            count++;
        }
        return prevNode;
    }

答案 8 :(得分:0)

保持双指针(curr,prev)最初都将指向列表的头部。

在列表上执行循环,直到您到达列表末尾或所需节点。

对于每次迭代,将curr节点移动到下一个,但在移动到下一个存储之前将其指针存储在prev指针中。

    prev = curr; // first store current node in prev
    curr = curr->next // move current to next

在循环结束时,prev节点将包含前一个节点。

getPrev(head, key) {    
    Node* curr = head;
    Node* prev = head;
    while(curr !=null && curr->data==key){
        prev = curr;
        curr = curr->next
    }
    return prev
}

实施例

list = 1-&gt; 5-> 10-> 4-> 3

我们想要4个So键= 4的头节点和此处的头点为

最初:

  • temp将指向1
  • prev将指向1

迭代1:

  • 首先,指定prev = temp(prev point to 1)
  • 移动温度; temp-&gt; next(temp point to 5)

迭代2:

  • 首先,指定prev = temp(prev point to 5)
  • 移动温度; temp-&gt; next(temp point to 10)

迭代3:

  • 首先,指定prev = temp(prev point to 10)
  • 移动温度; temp-&gt; next(temp指向4)

迭代4:

  • temp-&gt; data == key,因此它将返回循环。
  • return prev node

答案 9 :(得分:0)

我们可以使用慢速指针和快速指针遍历LinkedList。 假设

  

快速指针return of( require(`../../../assets/mydata.json`).pipe( map((listItems: ListItem[]) => { return { listItems: listItems }; }) ) );

     
    

慢指针fast = fast.next.next

  

慢指针将始终是快指针的前一个,因此我们可以找到它。

答案 10 :(得分:0)

您可以这样操作..您可以将当前节点的值替换为下一个节点的值..在第二个倒数第二个节点的下一个中,可以将null设置为空。就像从字符串中删除元素一样。这是代码

void deleteNode(ListNode* node) {
    ListNode *pre=node;
   while(node->next) 
    {
        node->val=node->next->val;
        pre=node;
        node=node->next;
    }
    pre->next=NULL;

}

答案 11 :(得分:-1)

假设您正在使用前向单链表,您的代码应该看起来像

while(node)
{
      previous = node
      node = node.next
      // Do what ever you want to do with the nodes
}