链表编写及相关算法练习

1.链表编写

/**ILink是定义的链表操作标准接口*/
public class LinkList<E> implements ILink<E> {
    private Node sentry;        //哨兵节点
    private Node rear;          //尾节点
    private int size;			//链表元素个数
    private int index;      //遍历的指针


    /*内部类**/
    private class Node{
        private E data;
        private Node next;
        public Node(E data){
            this(data,null);
        }
        public Node(E data,Node next){
            this.data = data;
            this.next = next;
        }

    }

    public LinkList(){
        sentry = new Node(null);
        this.rear = this.sentry;
    }
    
    //省略新增等基本操作

}

2.单链表反转实现

2.1 迭代反转链表

解释:定义三个指针,遍历节点的过程中改变节点指向即可(mid指针),移动指针的顺序分别是beg,mid,end

    /**
     * 单链表反转操作-迭代反转链表
     * @return
     */
    public void reverse() {
        Node beg = null;
        Node mid = this.sentry;
        Node end = mid.next;

        while(true){
            if(end == null){
                break;
            }
            mid.next = beg;
            beg = mid;
            mid = end;
            end = end.next;
        }
        mid.next = beg;
        this.sentry = mid;
        TraversalRev(this.sentry);
    }

    /**递归遍历*/
    public void TraversalRev(Node node){
        System.out.println(node.data);
        if(node.next == null){
            return;
        }else{
            TraversalRev(node.next);
        }
    }

2.2 头插法反转链表

解释:跟入栈的思想一致,注意指针丢失

    public void reverse2(){
        Node newHead = null;
        Node nextNode = this.sentry.next;
        while(true) {
            if (nextNode == null) {
                break;
            } else {
                //先取接下来的节点
                Node temp = nextNode.next;
                //让新的头结点连到上一个点
                nextNode.next = newHead;
                //将新头结点指针指向新头结点
                newHead = nextNode;
                //继续遍历下来的点
                nextNode = temp;
            }
        }
        this.sentry.next = newHead;
    }

3.链表中环的检测

3.1 链表中环的检测本质是判断存储指针的部分是否有重复即可

    /**
     * 同一个节点会不会被多个节点的next所存储
     * 遍历所有节点,设置一个Set,将存储的节点地址存入,如果重复就有环
     * @return
     */
    @Override
    public boolean isLoop() {
        Set<Node> nodeSet = new HashSet<>();
        Node node = this.sentry;
        while (node != null){
            //存在返回false
            if(!nodeSet.add(node.next)){
                return true;
            }
            node = node.next;
        }
        return false;
    }

3.2 龟兔赛跑算法-即快慢指针,如果链表中存在环,二者一定会在某一时刻相遇

    /**
     * 快慢指针,如果没有环 二者不会相遇
     * @return
     */
    @Override
    public boolean isLoop2() {
        Node slow = this.sentry;
        Node fast = this.sentry;
        while(fast != null || fast.next != null){
            slow = slow.next;
            fast = fast.next.next;
            if(slow == fast){
                return true;
            }
        }
        return false;
    }

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值