Offer 驾到,掘友接招!我正在参与2022春招打卡活动,点击查看活动详情。
一、题目描述
给你一个链表,每 k 个节点一组进行翻转,请你返回翻转后的链表。k 是一个正整数,它的值小于或等于链表的长度。如果节点总数不是 k 的整数倍,那么请将最后剩余的节点保持原有顺序。
**输入:**head = [1,2,3,4,5], k = 2 输出: [2,1,4,3,5]
二、思路分析
- k个一组反转链表是基于反转链表1和翻转链表2题目基础上,进一步深入,细节处理会稍微麻烦一些。
- 首先创建一个头结点,避免边界处理有麻烦,遍历
tail
,每组结点的tail
为组内最后一个元素,如果tail
为空,则代表不满k
个,当前组不需要翻转,直接返回链表。 - 当前组
tail
的后一个节点为下一组的头节点记录为nextGroupHead
,pre.Next
为当前组的第一个节点。 - 反转链表后,head为最后一个节点,tail为头部节点,pre.next指向tail,head.Next指向下一组的head。
- 更新pre到当前组尾部,即pre =head,head到下一组头部,即head = nextGroupHead。
三、AC 代码
func reverseKGroup(head *ListNode, k int) *ListNode {
dummynode := &ListNode{Next:head}
pre := dummynode
for head != nil {
tail := pre
for i :=0;i<k;i++ {
tail = tail.Next
if tail == nil {
return dummynode.Next
}
}
//记录tail后一个节点,以及pre后一个节点
nextGroupHead := tail.Next
head = pre.Next
//反转
reverseList(head,tail)
//拼接
pre.Next = tail
head.Next = nextGroupHead
//更新pre和head
pre = head
head = nextGroupHead
}
return dummynode.Next
}
func reverseList(head *ListNode,tail *ListNode) {
var pre *ListNode
cur := head
for pre != tail{
next := cur.Next
cur.Next = pre
pre = cur
cur = next
}
}
四、总结
k个一组反转链表,如果处理过反转链表1与翻转链表2,就会稍微简单一些。有一些细节要注意,比如建立头结点、翻转后的头尾节点互换后变量名使用会有一些绕,多做几次就会比较熟练。