148.排序链表
1.题目描述:
在 O(n log n) 时间复杂度和常数级空间复杂度下,对链表进行排序。
2.解题思路及代码:
看到O(n log n)时间复杂度,第一时间想到用归并排序或者快排,但是链表交换节点太麻烦,遂选择归并排序
用归并排序排序数组难点在于如何快速找到链表中点,便于后续递归调用。后来看了题解中大牛的解法后恍然大悟,使用快慢双指针,快指针一次走两步,慢指针一次走一步,快指针到达表尾时慢指针指向的结点便是中点结点。
解决了此问题以后,其余部分便和数组排序相差无几,代码如下:
/** * Definition for singly-linked list. * public class ListNode { * int val; * ListNode next; * ListNode(int x) { val = x; } * } */ 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){ fast=fast.next.next; slow=slow.next; } ListNode tmp=slow.next; slow.next=null; ListNode i=sortList(head); ListNode j=sortList(tmp); //归并 ListNode help=new ListNode(0); ListNode res=help; while(i != null&&j != null){ if(i.val<j.val){ help.next=i; i=i.next; }else{ help.next=j; j=j.next; } help=help.next; } while(i!=null){ help.next=i; i=i.next; help=help.next; } while(j!=null){ help.next=j; j=j.next; help=help.next; } return res.next; } }
解题思路参考:https://leetcode-cn.com/problems/sort-list/solution/sort-list-gui-bing-pai-xu-lian-biao-by-jyd/