题目描述
思路
与反转链表略有不同,此题要求反转区间内的链表,其实总体思路和反转全链表是差不多的,不过因为是区间内反转,指针指向稍微要复杂一些。可以通过画图来理解整个过程。
方法一:双指针反转
借用leetcode评论区dalao的一张图,通过图解可以理解整个过程
代码如下:
class Solution {
public ListNode reverseBetween(ListNode head, int left, int right) {
//定义一个虚拟头结点,方便处理
ListNode dummy = new ListNode(0);
dummy.next = head;
ListNode hh = dummy;
//找到left的前驱节点
for(int i = 1;i < left;i++) {
hh = hh.next;
}
ListNode a = hh.next;
ListNode b = a.next;
int k = right - left;
//对left到right位置的节点进行反转
while(k-- > 0) {
ListNode temp = b.next;
b.next = a;
a = b;
b = temp;
}
//将left前驱节点指向right节点
hh.next.next = b;
//将left节点指向最后一个节点
hh.next = a;
return dummy.next;
}
}
方法二:头插法反转
头插法就是每次反转时通过改变指针方向,将当前节点的下一个节点插入到当前节点的前面,实现反转。同样地,借用leetcode评论区dalao的一张图,通过图解可以理解整个过程
代码如下:
class Solution {
public ListNode reverseBetween(ListNode head, int left, int right) {
//定义一个虚拟头结点,方便处理
ListNode dummy = new ListNode(0);
dummy.next = head;
ListNode hh = dummy;
//找到left的前驱节点
for(int i = 1;i < left;i++) {
hh = hh.next;
}
//找到left节点
ListNode a = hh.next;
int k = right - left;
//使用头插法,每次循环将后一个节点插入到当前节点的前面
while(k-- > 0) {
ListNode temp = a.next;
a.next = a.next.next;
temp.next = hh.next;
hh.next = temp;
}
return dummy.next;
}
}