[C++]LeetCode: 125 Sort List (归并排序链表)
来源:互联网 发布:天猫淘宝京东哪个好 编辑:程序博客网 时间:2024/06/02 08:33
题目:Sort a linked list in O(n log n) time using constant space complexity.
思路:题目要求我们使用常数空间复杂度,时间复杂度为O(nlog(n)). 满足这个时间复杂度的有快速排序,归并排序,堆排序。插入排序时间复杂度为O(n^2). 双向链表用快排比较合适,堆排序也可用于链表,单项链表适合于归并排序。我们就用归并排序的思想来完成链表的排序。
首先是用快慢双指针找到链表中间的位置,然后分成前后端分别递归的归并排序,最后合并。
这道题的归并排序思想,我们在Merge Two Sorted Lists中已经做过。我们需要每次找到中点,然后对左右进行递归,最后用Merge Two Sorted Lists把他们合并起来。
Attention:
1. 快慢指针找中间节点的方法,是常用方法,要熟练使用。
//将链表分成前后两部分 双指针找到中间节点 ListNode* fast = head; ListNode* slow = head; while(fast->next != NULL && fast->next->next != NULL) { slow = slow->next; fast = fast->next->next; }2. 链表的数据结构是如何实现归并的方法的。定义一个合并后的链表,然后把合适的节点放进去。思想和数组是一样的,只是链表操作不一样。
复杂度:如果这里我们考虑递归的栈空间的话,空间复杂度是O(lg(n))
AC Code:
/** * Definition for singly-linked list. * struct ListNode { * int val; * ListNode *next; * ListNode(int x) : val(x), next(NULL) {} * }; */class Solution {public: ListNode *sortList(ListNode *head) { if(head == NULL || head->next == NULL) return head; //将链表分成前后两部分 双指针找到中间节点 ListNode* fast = head; ListNode* slow = head; while(fast->next != NULL && fast->next->next != NULL) { slow = slow->next; fast = fast->next->next; } ListNode* head2 = slow->next; slow->next = NULL; ListNode* head1 = head; head1 = sortList(head1); //前半段归并排序 head2 = sortList(head2); //后半段归并排序 return merge(head1, head2); }private: ListNode* merge(ListNode* h1, ListNode* h2) { ListNode* dummyhead = new ListNode(0); ListNode* mlist = dummyhead; while(h1 != NULL && h2 != NULL) { if(h1->val <= h2->val) { mlist->next = h1; h1 = h1->next; } else { mlist->next = h2; h2 = h2->next; } mlist = mlist->next; } if(h1 != NULL) { mlist->next = h1; } if(h2 != NULL) { mlist->next = h2; } return dummyhead->next; }};
我们也可以不使用递归的方法,自底向上的非递归版本的归并排序,空间复杂度就是常数了。可以看下这篇博文:sort list.
排序是面试中很常见和基础的一个主题,我们需要对各种常见的排序算法要熟悉。尤其是算法的原理,很多题目虽然没有直接考察排序的实现,但是会用到其中的思想,比如经典的topK问题,用到了快排的原理。这篇文章中有提到,可以看看:Median of Two Sorted Arrays.所以我们应该要更加注重排序算法的原理。
0 0
- [C++]LeetCode: 125 Sort List (归并排序链表)
- Leetcode Sort List 链表归并排序
- leetcode:Sort List(链表的归并排序)
- LeetCode Sort List 链表的归并排序
- leetcode 148. Sort List 链表归并排序
- sort list leetcode (归并排序)
- Sort List 归并排序链表
- 148. Sort List 链表归并排序
- Leetcode:Sort List 对单链表归并排序
- 【leetcode 单链表归并排序】Sort List
- 【LeetCode】 sort list 单链表的归并排序
- [leetcode] 134 Sort List (链表 & 归并排序)
- LeetCode Sort List(单链表归并排序)
- [C++]LeetCode: 126 Insertion Sort List (插入排序链表)
- 【LeetCode】Sort List 解题报告(对链表进行归并排序)
- Leetcode: Sort List - 归并
- 归并排序---Sort List
- Sort List——链表的快速/归并排序
- c++从键盘接受字符串简单
- 从头学习C#(1)
- android:style/Theme
- 判断程序是否在虚拟机中运行
- Android中Activity启动模式详解,可以控制程序按home键后进来还会调用一个自己不喜欢的界面
- [C++]LeetCode: 125 Sort List (归并排序链表)
- 写数据到手机内存
- Objective-C中的锁
- oracle trunc()函数用法-2
- Java利用回溯思想解决迷宫问题(寻找最短路径)
- 给Fragment设置style
- SQL Server 存储过程
- 为什么不能直接通过IP访问网站
- 中软优惠 等你加入