K 个一组翻转链表
给你链表的头节点 head ,每 k 个节点一组进行翻转,请你返回修改后的链表。
k 是一个正整数,它的值小于或等于链表的长度。如果节点总数不是 k 的整数倍,那么请将最后剩余的节点保持原有顺序。
你不能只是单纯的改变节点内部的值,而是需要实际进行节点交换。
参考后面图片看代码,事半功倍!!
/**
* Definition for singly-linked list.
* public class ListNode {
* int val;
* ListNode next;
* ListNode() {}
* ListNode(int val) { this.val = val; }
* ListNode(int val, ListNode next) { this.val = val; this.next = next; }
* }
*/
class Solution {
public ListNode reverseKGroup(ListNode head, int k) {
ListNode dummy =new ListNode(0);
dummy.next=head;
ListNode pre = dummy;
ListNode end = dummy;
while(end.next!=null){
//特殊情况,当翻转部分长度不足 k 时,在定位 end 完成后,end==null,已经到达末尾,说明题目已完成,直接返回即可.
for(int i =0 ; i < k && end!=null ; i++){
end=end.next;
}
if(end==null){
break;
}
//标记反转链表的前驱
ListNode start =pre.next;
//标记反转链表的后继(记录后驱,方便反转后的重新连接)
ListNode next =end.next;
//先断开k后面的链接,进行反转
end.next=null;
//反转后,进行连接
pre.next=reverse(start);
start.next=next;
//重置pre 和 end 指针,进行下一次的k反转
pre =start;
end=pre;
}
return dummy.next;
}
// 经典的反转链表
public ListNode reverse(ListNode head){
ListNode pre = null;
ListNode curr =head;
while(curr!=null){
ListNode next=curr.next;
curr.next=pre;
pre=curr;
curr=next;
}
return pre;
}
}