Day4 | | 24. 两两交换链表中的节点 ,19.删除链表的倒数第N个节点 , 面试题 02.07. 链表相交

  1. 两两交换链表中的节点
    1、1虚拟节点
    Day4 | | 24. 两两交换链表中的节点 ,19.删除链表的倒数第N个节点 , 面试题 02.07. 链表相交_第1张图片要注意一点:使用虚拟的节点的意义就是想让头节点和其他节点一样,所以在定义returnHead的时候应该定义成
    ListNode returnHead = dummy; return returnHead.next;
    而不能是
    ListNode returnHead = head;
    return head;
    比如 0 1 2
    交换完是 1 0 2
    如果返回head
    就会是0 2
 public static ListNode swapPairs(ListNode head) {
        //虚拟节点
        ListNode dummy = new ListNode(0,head);
        //需要一个节点保存现在的头节点 用于返回 但不能直接保存head 因为这个head的位置也是要参与交换的
        //ListNode returnHead = head;
        ListNode returnHead = dummy;
        //这个节点作为临时节点 和dummy还有temp一起变化
        ListNode cur = head;
        while (cur != null && cur.next != null){
            ListNode temp = cur.next.next; // 缓存 next
            dummy.next = cur.next;// 将 prev 的 next 改为 head 的 next
            cur.next.next = cur;// 将 head.next(prev.next) 的next,指向 head
            cur.next = temp; // 将head 的 next 接上缓存的temp
            dummy = cur;// 步进1位
            cur = cur.next;// 步进1位
        }
        return returnHead.next;
    }

19.删除链表的倒数第N个节点
思路 快慢指针
使用虚拟头节点
让快指针先走n+1
然后快慢指针一起走 直到快指针指向null
慢指针就指向的目标节点的前一个节点
Day4 | | 24. 两两交换链表中的节点 ,19.删除链表的倒数第N个节点 , 面试题 02.07. 链表相交_第2张图片

/**
     *思路 快慢指针
     * 使用虚拟头节点
     * 让快指针先走n+1
     * 然后快慢指针一起走 直到快指针指向null
     * 慢指针就指向的目标节点的前一个节点
     */
    public static ListNode removeNthFromEnd(ListNode head, int n) {
        //    链表中结点的数目为 sz
        //    1 <= sz <= 30
        //    0 <= Node.val <= 100
        //    1 <= n <= sz
        ListNode dummy = new ListNode(0,head);
        ListNode fast = dummy;
        ListNode slow = dummy;

        for (int i = 0; i <= n; i++) { //让fast先走n+1
            fast = fast.next;
        }
        while (fast != null){
            fast = fast.next;
            slow = slow.next; //快慢指针一起移动
        }
        slow.next = slow.next.next;
        return dummy.next;
    }

面试题 02.07. 链表相交 同:160.链表相交
这里要注意,交点不是数值相等,而是指针相等
思路:把两条链表尾端对其,然后长链表移动到和短链表头节点的位置,比较两条链表是否相等,不相等就往后挪一位,直到相等或为null

ListNode listNode7 = new ListNode(6, null);
ListNode listNode6 = new ListNode(2, listNode7);
ListNode listNode5 = new ListNode(6, listNode6);
ListNode listNode4 = new ListNode(5, listNode5);
ListNode listNode3 = new ListNode(4, listNode4);

// ListNode listNode2 = new ListNode(6, null);
ListNode listNode1 = new ListNode(2, listNode6);
ListNode listNode0 = new ListNode(1, listNode1);
ListNode listNode = getIntersectionNode(listNode0,listNode3);

这样才会返回2 6

142.环形链表II
Day4 | | 24. 两两交换链表中的节点 ,19.删除链表的倒数第N个节点 , 面试题 02.07. 链表相交_第3张图片

 public ListNode detectCycle(ListNode head) {
        ListNode fast = head;
        ListNode slow = head;
        while (fast!=null && fast.next != null){ //fast.next != null fast一次走两个
            fast = fast.next.next;
            slow = slow.next;
            if(fast == slow){ //说明有环 而且相遇
                ListNode index1 = fast;
                ListNode index2 = head;
                // 两个指针,从头结点和相遇结点,各走一步,直到相遇,相遇点即为环入口
                while (index1 != index2){
                    index1 = index1.next;
                    index2 = index2.next;
                }
                return index1;
            }
        }
        return null;
    }

你可能感兴趣的:(链表,java,数据结构)