206.反转链表
206.反转链表
题目
给你单链表的头节点 head ,请你反转链表,并返回反转后的链表。
要求:空间复杂度 O(1) ,时间复杂度 O(n)
示例 1:
输入:head = [1,2,3,4,5]
输出:[5,4,3,2,1]
示例 2:
输入:head = [1,2]
输出:[2,1]
示例 3:
输入:head = []
输出:[]
提示:
链表中节点的数目范围是 [0, 5000]
-5000 <= Node.val <= 5000
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/reverse-linked-list
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
题解-迭代
迭代方法是从头到尾依次改变
class Solution {
public ListNode reverseList(ListNode head) {
ListNode pre = null; //指向前一个,,防止断链
ListNode tmp = null; // 保存后一个,防止断链
while(head != null){
tmp = head.next;
head.next = pre;
pre = head;
head = tmp;
}
return pre;
}
}
时间复杂度:O(N),其中 N 是链表的长度。需要遍历链表一次。
空间复杂度:O(1),常数空间复杂度
题解-递归
递归是先从头到尾,找到尾之后,再从尾到头依次返回。所以递归一半写在处理的前面。先递归再处理。
递归最重要的就是,认为当前递归已经帮我处理好了我想处理的事情,只需要考虑本层递归即可,也就是看局部不看全局
递归三部曲
本层递归需要做什么事情
本层递归需要进行反转,我们只看局部的两个元素假设3->4,只要变成4->3就行了。
head.next.next = head;
head.next = null;
递归的终止条件与递归返回值是什么?
什么时候终止?
细分需要交换两个元素,那么只有一个元素或者没有元素就可以不用交换了。
返回值是什么?
我们的是最终处理好的链表,也就是链表的最后一个元素,我们可以在最后一层递归中,把指向这个元素的指针返回,也就是说我们需要把最内层的递归返回值6层层传递出来,其他层递归返回的也是这个6。
或者说是返回处理好交换后的链表
public ListNode reverseList(ListNode head) {
if(head ==null || head.next ==null ) return head; //一个元素和空元素时不需要交换
ListNode p = reverseList(head.next);//指向最后一个元素的指针层层返回,先递归到最后(递归的深度是链表的长度),再从最后开始处理,先递归再处理
head.next.next = head;
head.next = null;
return p;
}
时间复杂度:O(N),其中 N 是链表的长度。需要对链表的每个节点进行反转操作。
空间复杂度:O(N),其中 N 是链表的长度。空间复杂度主要取决于递归调用的栈空间,递归的深度是链表的长度,最多为 N 层