简体   繁体   English

将第一个节点插入空双链表中[如何]

[英]inserting first node into empty doubly-linked list [how to]

This is a follow-on to a previous post . 这是上一篇文章的后续文章 I am now looking at how to insert a first node into an empty doubly-linked list. 我现在正在研究如何将第一个节点插入到空的双向链接列表中。 It's kind of tricky at first it seems...i would be grateful for a hint as to what is missing in my addFirst method 乍一看似乎有点棘手...对于我的addFirst方法缺少的内容我将不胜感激

...
public DLL()
{
    first = null ;
    last = null ;
}

...
DLL myList = new DLL() ;
DLLNode A = new DLLNode("Hello", null, null) ;
...

myList.addFirst(A) ;

...
public void addFirst(DLLNode v)
{
    v.pred = first ;
    v.succ = last ; 
}

[EDIT] [编辑]

Solution as proposed by typo.pl: typo.pl提出的解决方案:

public void addFirst(DLLNode v)
{
    v.pred = first ;
    v.succ = last ;
    first = v ;
    last = v ;
}

You've only updated the node's information. 您只更新了节点的信息。

Now you need to update the DLL's information as to what the first/last nodes in the list are. 现在,您需要更新有关列表中第一个/最后一个节点是什么的DLL信息。 And it's really easy to update when you're adding one node to an empty list. 当您将一个节点添加到空列表时,更新确实很容易。 There's only one choice for first node and one choice for last node. 第一个节点只有一个选择,最后一个节点只有一个选择。

you can do something like that 你可以做这样的事情

public void addFirst(DLLNode v){

    v.pred = null ; //v will be first node so its pred. is null
    v.succ = first; //v successor is the old first node

    if (first != null)
        first.pred = v; //the first pred. is the new node

    first  = v;     //v is now the first node in the linked list

    //if that was the first node to add , update the last pointer                    
    if (last == null)
       last = v;
}

you can also use Sentinel nodes 您还可以使用Sentinel节点

You can actually improve on this by pretending that you're using a circularly linked list: 实际上,您可以通过假装使用循环链接列表来改善此情况:

public class DLLNode {
    Object contents;
    DLLNode next, prev;
}

public class DLL extends DLLNode {
    public DLL() {
        // next and prev are the first and last entry
        // but they are set to this to indicate an empty list
        next = prev = this;
    }
    public void push(DLLNode v) {
        v.next = this;
        v.prev = this.next;
        this.next.prev = v;
        this.next = v;
    }
    public void shift(DLLNode v) {
        v.prev = this;
        v.next = this.prev;
        this.prev.next = v;
        this.prev = v;
    }
    public DLLNode pop() {
        return this.remove(this.next);
    }
    public DLLNode unshift() {
        return this.remove(this.prev);
    }
    public DLLNode remove(DLLNode v) {
        if (v == this) throw new IllegalArgumentException();
        v.next.prev = v.prev;
        v.prev.next = v.next;
        v.next = null;
        v.prev = null;
        return v;
    }
}

Note how push works even when the list is empty: this.next is the same as this and this.next.prev is the same as this.prev. 请注意,即使列表为空,push的工作方式也是如此:this.next与this相同,this.next.prev与this.prev相同。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM