题⽬描述

给定单向链表的头指针和⼀个要删除的节点的值,定义⼀个函数删除该节点。返回删除后的链表的头节点。

  1. 此题对⽐原题有改动

  2. 题⽬保证链表中节点的值互不相同

  3. 该题只会输出返回的链表和结果做对⽐,所以若使⽤ C 或 C++ 语⾔,你不需要 free 或 delete 被删除的节点

数据范围:

  • 0<=链表节点值<=10000

  • 0<=链表⻓度<=10000

示例1

示例2

思路及解答

虚拟头节点

如果要删除链表⾥⾯的⼀个节点,其实就是将前置节点的next 直接指向当前节点的后置节点,这样在链表中再也找不到该节点了,也就是相当于删除了。

假设有⼀个链表,我们需要删除⾥⾯的 5 : ⾸先需要判断链表头结点是不是为空,如果为空,那么就直接返回NULL,如果等于我们要找的,那么直接返回下⼀个节点引⽤即可。

如果不符合以上说的,那么我们需要新建⼀个前置节点pre ,与现在的链表连接在⼀起: 然后初始化⼀个 cur 节点表示当前节点,指向 head 节点: cur 不为空, cur 和 pre 后移: 发现 cur 正是我们需要查找的 5,那么记录下 5 的下⼀个节点 1 ,也就是next : cur 的 next 指向 NULL ,使⽤ pre 的 next 指向刚刚记录的 next : 简化链表也就是: 取之前虚拟的头结点的后⼀个节点,就是删除掉之后的新链表:

迭代

通过遍历链表找到目标节点并修改指针,维护前驱指针,当找到目标节点时修改指针跳过该节点。这个和上面方法类似,只是不同写法

  • 时间复杂度:O(n),最坏情况下需要遍历整个链表

  • 空间复杂度:O(1),只使用常数空间

递归

当前节点是要删除的节点则返回next,否则递归处理剩余链表

  • 时间复杂度:O(n),需要处理每个节点

  • 空间复杂度:O(n),递归调用栈的深度