算法(TS): 反转链表

反转链表

给你单链表的头节点 head ,请你反转链表,并返回反转后的链表。

示例一

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

输出:[5,4,3,2,1]

示例二

输入:head = [1,2]

输出:[2,1]

示例三

输入:head = []

输出:[]

提示:

  • 链表中节点的数目范围是 [0, 5000]
  • -5000 <= Node.val <= 5000

进阶: 链表可以选用迭代或递归方式完成反转。你能否用两种方法解决这道题?

解法一

  1. 得到链表中节点的总数,total,这里使用 while 语句
  2. 将从头遍历链表,将第n个节点与第total-n个节点的val交换,为了得到total-n个节点需要遍历链表

这种做法并没有反转 Node 实例,只是将它们的值反转了

ts 复制代码
/**
 * 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)
 *     }
 * }
 */

function getNode(head: ListNode,NO: number) {
    let n = 1

    while(head && n < NO) {
        head = head.next
        n++
    }

    return head
}

function reverseList(head: ListNode | null): ListNode | null {
    let total = 0
    let p = head
    while(p) {
        p = p.next
        total ++
    }
    p = head
    let n = 0
    let middle = Math.floor(total / 2)
    while(p && n < middle) {
        const other = getNode(head,total-n)
        const temp = p.val
        p.val = other.val
        other.val = temp
        p = p.next
        n++
    }
    return head
};

时间复杂度O(n * n),空间复杂度O(1)

解法二

解法一在查找 total-n 位置上的节点存在重复计算,解法二有一个 Map 保存节点的位置,必须重复计算。

这种做法并没有反转 Node 实例,只是将它们的值反转了

ts 复制代码
function reverseList(head: ListNode | null): ListNode | null {
    let total = 0
    let p = head
    const nodeMap = new Map<number, ListNode>()
    while(p) {
        total ++
        nodeMap.set(total,p)
        p = p.next
    }
    p = head
    let n = 0
    let middle = Math.floor(total / 2)
    while(p && n < middle) {
        const other = nodeMap.get(total-n)
        const temp = p.val
        p.val = other.val
        other.val = temp
        p = p.next
        n++
    }
    return head
};

时间复杂度O(n),空间复杂度O(n)

解法三

创建两个指针 result 和 prev,result 是最新的结果链表,prev 是上一次得到的结果链表,它们的初始值都为 null,遍历 head,result 和 prev 的关系是 result.next = prev,

vbscript 复制代码
/**ts
 * 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)
 *     }
 * }
 */

function reverseList(head: ListNode | null): ListNode | null {
    let result = null
    let prev = null
    while(head) {
        prev = result
        result = head
        head = head.next
        result.next = prev
    }
    return result
};

时间复杂度O(n),空间复杂度O(1)

相关推荐
不懒不懒5 分钟前
【逻辑回归从原理到实战:正则化、参数调优与过拟合处理】
人工智能·算法·机器学习
一只大袋鼠6 分钟前
分布式 ID 生成:雪花算法原理、实现与 MyBatis-Plus 实战
分布式·算法·mybatis
tobias.b9 分钟前
408真题解析-2010-27-操作系统-同步互斥/Peterson算法
算法·计算机考研·408真题解析
寄存器漫游者18 分钟前
数据结构 二叉树核心概念与特性
数据结构·算法
m0_7066532321 分钟前
跨语言调用C++接口
开发语言·c++·算法
皮皮哎哟24 分钟前
数据结构:从队列到二叉树基础解析
c语言·数据结构·算法·二叉树·队列
D11_30 分钟前
[特殊字符]️ 5379工具箱 - 全部网站链接汇总
服务器·百度·阿里云·typescript·编辑器
一匹电信狗32 分钟前
【高阶数据结构】并查集
c语言·数据结构·c++·算法·leetcode·排序算法·visual studio
愚者游世1 小时前
list Initialization各版本异同
开发语言·c++·学习·程序人生·算法
.小墨迹1 小时前
apollo中车辆的减速绕行,和加速超车实现
c++·学习·算法·ubuntu·机器学习