算法合集 | 链表 | Leetcode 24. 两两交换链表中的节点

71 阅读2分钟

开启掘金成长之旅!这是我参与「掘金日新计划 · 12 月更文挑战」的第5天,点击查看活动详情

前言

本系列文章主要会总结一些常见的算法题目以及算法的易错点,难点,以及一些万用的公式,并且结合实际的 Leetcode 题目来进行加深理解以及实际应用,算法这种东西,属于是一到用时方恨少的类型,在平时总结一些常见的简单算法,经常磨练自己的算法思维,对于日常的开发还是能有不少的帮助的。

  • 今天来介绍一下两两交换链表中的节点的操作

怎么两两交换链表中的节点

下面是一个正常的链表,里面有四个元素,最后指向null

图片.png

就针对于上图来说,我们要两两交换的话,就需要把前面的结点 1 2 以及后面的结点 3 4 进行两两交换,变为:

图片.png

对于后面的结点3和结点4的交换是比较简单的,只需要把结点3的前一个结点的指向改为结点4,把结点4的指向改为结点3,结点3的指向改为结点4的指向,再上图也就是null。

难点在于前面的结点1和结点2进行交换,结点1的指向要由结点2改为结点3,结点2的指向由结点3改为结点1,这就和前面的结点3,4的交换有点不同,因为结点1之前是没有结点的,所以为了统一所有结点的处理,我们可以在结点1的前面加上虚拟头结点 dummyHead

图片.png

这样对于所有的结点就可以采用同样的操作了。

然后交换指针指向的步骤如下,只要根据图中的交换顺序,先把头结点的指针改为结点2,再把结点2的指针改为结点1,再把结点1的指针改为结点3,以此类推,后面的结点3 结点4的互换也是一样的

图片.png

Leetcode 206.两两交换链表中的节点

在代码中就循环链表,只要当前结点和当前结点的下两个结点都不为null,就满足两两交换的条件,并且交换完成之后,要将当前结点改为两两交换后的后一个结点。剩下的交换过程就是上面图中所说的了。

/**
 * Definition for singly-linked list.
 * class ListNode {
 *     val: number
 *     next: ListNode | null
 *     constructor(val?: number, next?: ListNode | null) {
 *         this.val = (val===undefined ? 0 : val)
 *         this.next = (next===undefined ? null : next)
 *     }
 * }
 */
  
var swapPairs = function(head: ListNode): ListNode {
    const dummyHead = new ListNode(0);
    dummyHead.next = head;
    let cur = dummyHead;
    while (cur.next !== null && cur.next.next !== null) {
        const node1 = cur.next;
        const node2 = cur.next.next;
        cur.next = node2;
        node1.next = node2.next;
        node2.next = node1;
        cur = node1;
    }
    return dummyHead.next;
};

图片.png