Leecode链表的题目

目录

  • 1 链表题目
    • 1.1 移除链表元素
    • 1.2 两两交换链表中的节点
    • 1.3 链表相交
    • 1.4 链表相交剑指 Offer 25. 合并两个排序的链表
    • 1.5 142.环形链表II

1 链表题目

1.1 移除链表元素

Leecode链表的题目_第1张图片
  1. 思路
    1)首先设置一个新的链表头node,放入一个虚拟头结点
    2)设置一个循环,快指针遍历链表使用快慢指针,如果快指针指向目标值,那么慢指针指向就跳过快指针这个点;如果不指向,那么快慢指针相等。
    3)在判断完后,让快指针前进一位。
    4)最后输出node的next,去掉头结点。
  2. 代码
class Solution {
    public ListNode removeElements(ListNode head, int val) {
        //定义一个新的链表,加上虚拟头结点
        ListNode node=new ListNode(-1,head);
        ListNode pre=node;  //慢指针
        ListNode cur=pre.next;  //快指针
        while(cur!=null){
            if(cur.val==val){
                pre.next=cur.next;
            }else{
                pre=cur;
            }
            cur=cur.next;
        }
        return node.next
    }
}

1.2 两两交换链表中的节点

  1. 题目说明
    Leecode链表的题目_第2张图片

  2. 思路:
    1)首先设置头结点
    2)交换三步曲
    Leecode链表的题目_第3张图片

  3. 代码

class Solution {
    public ListNode swapPairs(ListNode head) {
        //1)设置一个虚拟头结点
        ListNode node=new ListNode(-1,head);
        //2)设置双指针,进行遍历交换
        ListNode cur=node;
        while(cur.next!=null && cur.next.next!=null ){
            ListNode temp=cur.next;
            ListNode temp1=cur.next.next.next;
            //交换连接三部曲
            cur.next=cur.next.next;
            cur.next.next=temp;
            cur.next.next.next=temp1;

            //更新cur的值
            cur=cur.next.next;  //一定要保证操作的是一个
        }
        return node.next;
    }
}
  1. 注意事项
    1)全程一定要保证操作的都是cur节点的状态

1.3 链表相交

  1. 题目说明
    Leecode链表的题目_第4张图片
  2. 思路展示
    1)a+c+b+c=b+c+a+c,把两个链表拼接起来,一定有一段是相同的
  3. 代码说明
public class Solution {
    public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
        //a+c+b+c=b+c+a+c:把两个链表相加起来,最后总有一个公共的c
        ListNode head1=headA;
        ListNode head2=headB;
        while(head1!=head2){
            head1=head1==null?headB:head1.next;
            head2=head2==null?headA:head2.next;
        }
        return head1; 
    }
}

1.4 链表相交剑指 Offer 25. 合并两个排序的链表

  1. 题目说明
    Leecode链表的题目_第5张图片

  2. 代码
    1)方法一:迭代法

class Solution {
    public ListNode mergeTwoLists(ListNode list1, ListNode list2) {
        //方法一:使用迭代方法
        ListNode result=new ListNode();
        ListNode temp=result;  //结果代理人

        //1)当两边都不为空时
        while(list1!=null &&list2!=null){
            if(list1.val<=list2.val){
                temp.next=list1;
                list1=list1.next;
            }else{
                temp.next=list2;
                list2=list2.next;
            }
            temp=temp.next;
        }
        //2)当一边为空时
        if(list1==null) temp.next=list2;
        if(list2==null) temp.next=list1;
        return result.next;
    }
}

2)方法二:递归法(思路需要掌握)

class Solution {
    public ListNode mergeTwoLists(ListNode list1, ListNode list2) {
        //递归方法

        //截止条件
        if(list1==null ) return list2;
        if(list2==null) return list1;

        //递归循环
        if(list1.val<=list2.val){
            list1.next=mergeTwoLists(list1.next,list2);
            return list1;
        }else{
            list2.next=mergeTwoLists(list1, list2.next);
            return list2;
        }
    }
}

1.5 142.环形链表II

  1. 题目说明
    Leecode链表的题目_第6张图片
  2. 思路说明
    1)首先判断是否存在环:通过快慢指针,看看快慢指针是否会相遇(快指针一次走两步,慢指针一次走一步)初始位置都为头
    2)在相遇的情况下,快指针位置不变,慢指针指向头结点,然后一步一步走,相遇的地方就是环入口。(涉及到一个数学的公式)
  3. 代码说明
public class Solution {
    public ListNode detectCycle(ListNode head) {
        //判断是否存在环:设置一个快慢指针:
        //快指针一次走两步,慢指针一次走一步
        //如果存在环,快指针是一步一步趋向于慢指针的
        ListNode fast=head;
        ListNode slow=head;
        while(fast!=null &&fast.next!=null){      //一定要对fast的后面两步进行判断,均非空才可
            fast=fast.next.next;                  //两个循环都是先走再判断。
            slow=slow.next;
            if(slow==fast){
                while(fast!=null){
                    ListNode temp=head;
                    temp=temp.next;
                    fast=fast.next; 
                    if(fast==temp) return fast;
                }
            }
        }
        return null;     
    }
}

你可能感兴趣的:(Leecode刷题,链表,list,数据结构)