刷题使我快乐,满脸开心.jpg
- 来源:CodeTop
- 链接:https://mp.weixin.qq.com/s/0WVa2wIAeG0nYnVndZiEXQ
题目
链表,奇数位置按序增长,偶数位置按序递减,如何能实现链表从小到大?(2020.10 字节跳动-后端)
奇偶生序倒序链表的重新排序组合,例如:18365472(2020.08 字节跳动-后端)
1->4->3->2->5
给定一个链表奇数部分递增,偶数部分递减,要求在O(n)
时间复杂度内将链表变成递增,5分钟左右(2020.07 字节跳动-测试开发)
奇数位升序偶数位降序的链表要求时间
O(n)
空间O(1)
的排序?(2020.07 字节跳动-后端)
示例 1:
输入:1->8->3->6->5->4->7->2->NULL
输出:1->2->3->4->5->6->7->8->NULL
思路
这道题难度应该是中等没啥问题,其实涉及的思路都比较基础,就是
- 拆分链表
- 反转偶数链表(转为升序)
- 合并链表
感觉无需说太多,主要是冷静分析,以及必要时一定不要单纯想象,实际画图模拟下~
代码
func do(root *ListNode) *ListNode {
if root == nil || root.Next == nil {
return root
}
veryHead1 := &ListNode{}
veryHead2 := &ListNode{}
head1 := veryHead1
head2 := veryHead2
// 拆分双链
i := 1
for root != nil {
if i%2 == 1 {
head1.Next = root
head1 = head1.Next
} else {
head2.Next = root
head2 = head2.Next
}
root = root.Next
i++
}
// 尾部清空,可能会因为指针引用地址没有变,造成混乱
head1.Next = nil
head2.Next = nil
// 翻转偶数链
// 为了清晰,不复用变量
now := veryHead2.Next
var pre, next *ListNode
for now != nil {
next = now.Next
now.Next = pre
pre = now
now = next
}
// 合并链表
// 为了清晰,不复用变量
veryHead := &ListNode{}
head := veryHead
head1 = veryHead1.Next
head2 = pre
for head1 != nil && head2 != nil {
if head1.Val > head2.Val {
head.Next = head2
head2 = head2.Next
} else {
head.Next = head1
head1 = head1.Next
}
head = head.Next
}
// 当有一个链空了,剩下的直接串上就好
if head1 == nil {
head.Next = head2
} else if head2 == nil {
head.Next = head1
}
return veryHead.Next
}