迭代
class Solution {
public ListNode reverseKGroup(ListNode head, int k) {
ListNode dummyHead = new ListNode(0, head);
ListNode prev = dummyHead;
ListNode end = dummyHead;
/**
* 设置两个指针,最终要指向每个k区间的头尾,其中end指针不断移动
* 如果end.next == null,说明链表全部遍历完了
*/
while (end.next != null) {
for (int i = 0; i < k && end != null; i++) {
end = end.next;
}
/**
* 判断剩余节点个数是否大于等于k
* 如果剩余节点个数小于k,则end == null,直接跳出循环
*/
if (end == null) {
break;
}
/**
* 找到一个完整的k区间,进行翻转
* 保存该区间的头节点和下一个区间的头节点
* 让该区间的尾节点指向null,然后进行翻转
*/
ListNode start = prev.next;
ListNode nextStart = end.next;
end.next = null;
prev.next = reverse(start);
/**
* 翻转完毕,尾节点变成start,接上下一个区间头节点
* 同时重置下一个prev和end
*/
start.next = nextStart;
prev = start;
end = prev;
}
return dummyHead.next;
}
/**
* 翻转链表
*/
public ListNode reverse(ListNode head){
if (head == null || head.next == null){
return head;
}
ListNode next = reverse(head.next);
head.next.next = head;
head.next = null;
return next;
}
}
/**
* 时间复杂度 O(n)
* 空间复杂度 O(1)
*/
递归
class Solution {
public ListNode reverseKGroup(ListNode head, int k) {
/**
* 终止条件
* 递归过程中head有可能为null。因此也需要判断
*/
if (head == null || head.next == null || k == 1){
return head;
}
ListNode dummyHead = new ListNode(0, head);
ListNode prev = dummyHead;
ListNode next;
/**
* 判断剩余节点个数是否大于等于k
* 如果剩余节点个数小于k,不用翻转直接返回
* 否则进行递归
*/
for (int i = 0; i < k && prev != null; i++) {
prev = prev.next;
if (prev == null){
return dummyHead.next;
}
}
next = reverseKGroup(prev.next, k);
/**
* 递归以后,只剩下前k个节点需要翻转
* 翻转以后,最后一个节点是head,和next接上
*/
prev.next = null;
ListNode newHead = reverse(head);
head.next = next;
return newHead;
}
/**
* 翻转链表
*/
public ListNode reverse(ListNode head){
if (head == null || head.next == null){
return head;
}
ListNode next = reverse(head.next);
head.next.next = head;
head.next = null;
return next;
}
}
/**
* 时间复杂度 O(n)
* 空间复杂度 O(n)
*/
https://leetcode-cn.com/problems/reverse-nodes-in-k-group/