前端算法(24)

43 阅读2分钟

本文已参与「新人创作礼」活动,一起开启掘金创作之路。

题目

给你一个链表,两两交换其中相邻的节点,并返回交换后链表的头节点。你必须在不修改节点内部的值的情况下完成本题(即,只能进行节点交换)。

输入: head = [1,2,3,4]
输出: [2,1,4,3]

题目解析

思路一

这里采用递归进行实现,我们每次递归需要确认返回值,这里返回值是两个节点的首节点或者单个节点的自身节点,也是是当前交换指针后的头节点,或者没有交换的 head 节点,在定义好递归的返回值后,就开始交换指针了,首先保存好 next 指针 然后 next.next = head ,head 指针指向下一个递归的头节点 当前计算的头节点是 next 指针

var swapPairs = function (head) {
// 少于两个节点的,直接返回本身即可
    if (!head || !head.next) return head 
    const next = head.next
    // 返回的下一次递归的首节点
    head.next = swapPairs(next.next)
    next.next = head
    // 返回交换后的首节点
    return next
};

思路二

我们采用迭代的方式进行实现,也是每两个节点往前进行交换指针,也和链表反转类似,关键在于有三个指针,分别指向前后和当前节点。先定义一个新链表emptyeNode,我们这里需要注意的是,需要保存prev指针作为连接每一次迭代的起点,然后prev.next 连接交换后的头节点,即 next 节点,在进行交换操作,通过交换 cur = next.next,next.next = cur,最后更改 prev 的值为下一次迭代的 prev,即当前的 cur 指针,最后返回 emptyNode.next

 var swapPairs = function (head) {
    const emptyeNode = new ListNode()
    emptyeNode.next = head
    let prev =emptyeNode
    while(prev.next && prev.next.next){
        const cur = prev.next,next = prev.next.next
        // prev 指针指向交换后的头节点
        prev.next = next
        cur.next = next.next
        next.next = cur
        // 设置新的 prev
        prev = cur 
    }
    return emptyeNode.next
 }