对双向链表的学习

本文详细介绍了一种使用双指向节点的数据结构——双向链表的实现方法。包括头插法、尾插法、任意位置插入、链表长度计算、查找、删除等核心操作。通过具体代码示例,展示了双向链表的基本特性和高效操作。

双指向的节点

package com.test;

public class DoubleLinkedNode {
    private int val;
    public DoubleLinkedNode prev = null;  //指向前一节点的指针
    public DoubleLinkedNode next = null;  //指向后一节点的指针
    public DoubleLinkedNode(int val){  //带参构造方法
        this.val = val;
    }
    //获得私有变量val
    public int getVal(){  
        return this.val;
    }
}

双向链表:

package com.test;

public class DoubleLinkedList {
    DoubleLinkedNode head = null;
    public DoubleLinkedList(){
        //创建一个傀儡节点
        head = new DoubleLinkedNode(-1);
        head.prev = head;
        head.next = head;
    }

    //头插法
    public void addFirst(int data){
        DoubleLinkedNode node = new DoubleLinkedNode(data);  //创建要插入的新节点
        DoubleLinkedNode next = head.next;  //跳过傀儡节点
        head.next = node;  
        node.prev = head;
        node.next = next;
        next.prev = node;
    }

    //尾插法
    public void addLast(int data){
        DoubleLinkedNode node = new DoubleLinkedNode(data);
        DoubleLinkedNode prev = head.prev;
        prev.next = node;
        node.prev = prev;
        node.next = head;
        head.prev = node;
    }

    //任意位置插入,第一个数据节点为0号下标
    public boolean addIndex(int index, int data){
        DoubleLinkedNode node = new DoubleLinkedNode(data);
        int size = size();
        //判定index取值是否合法
        if (index < 0 || index > size){
            return false;
        }
        //头插
        if (index == 0){
            addFirst(data);
            return true;
        }
        //尾插
        if (index == size){
            addLast(data);
            return true;
        }
        //一般插入
        DoubleLinkedNode cur = toFindIndex(index);
        DoubleLinkedNode prev = cur.prev;
        prev.next = node;
        node.prev = prev;
        node.next = cur;
        cur.prev = node;
        return true;
    }

    //求链表的长度
    public int size(){
        int size = 0;
        for (DoubleLinkedNode cur = head.next; cur != head; cur  = cur.next){
            size++;
        }
        return size;
    }

    //找到index位置的节点
    public DoubleLinkedNode toFindIndex(int index){
        int  i = 0;
        DoubleLinkedNode cur = head.next;
        while (i < index){
            cur = cur.next;
            i++;
        }
        return cur;
    }

    //查找链表中是否存在关键字key
    public boolean contains(int key){
        for (DoubleLinkedNode cur = head.next; cur != head; cur = cur.next){
            if (cur.getVal() == key){
                return true;
            }
        }
        return false;
    }

    //删除第一次出现关键字为key的节点
    public void remove(int key){
        DoubleLinkedNode cur = toFindNode(key);
        //未找到要查找的节点
        if (cur == null){
            return;
        }
        //找到要查找的节点
        DoubleLinkedNode prev = cur.prev;
        DoubleLinkedNode next = cur.next;
        prev.next = next;
        next.prev = prev;
    }

    //删除所有值为key的节点
    public void removeAll(int key){
        while (true){
            DoubleLinkedNode cur = toFindNode(key);
            //未找到关键字为key的节点
            if(cur == null){
                return;
            }
            //找到要删除的关键字为key的节点
            DoubleLinkedNode prev = cur.prev;
            DoubleLinkedNode next = cur.next;
            prev.next = next;
            next.prev = prev;
        }
    }

    //找到关键字为key的节点
    public DoubleLinkedNode toFindNode(int key){
        for (DoubleLinkedNode cur = head.next; cur != head; cur = cur.next){
            if (cur.getVal() == key){
                return cur;
            }
        }
        return null;
    }

    //输出链表
    public void display(){
        System.out.println();
        //正向输出
        System.out.print("正向:");
        System.out.print("[");
        for (DoubleLinkedNode cur = head.next; cur != head; cur = cur.next){
            if (cur.next != head){
                System.out.print(cur.getVal() + ",");

            }else{
                System.out.print(cur.getVal() + "]");
            }
        }
        System.out.println();
        //反向输出
        System.out.print("反向:");
        System.out.print("[");
        for (DoubleLinkedNode cur = head.prev; cur != head; cur = cur.prev){
            if (cur.prev != head){
                System.out.print(cur.getVal() + ",");

            }else{
                System.out.print(cur.getVal() + "]");
            }
        }
    }
}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值