关于链表的排序
代码:java
题目描述
在O(n log n)的时间内使用常数级空间复杂度对链表进行排序。
Sort a linked list in O(n log n) time using constant space complexity.
节点定义
/**
* Definition for singly-linked list.
* class ListNode {
* int val;
* ListNode next;
* ListNode(int x) {
* val = x;
* next = null;
* }
* }
*/
思路
类似快排,根据第一个节点从前往后扫
小于放入一个链表,大于放入一个链表,等于放入一个链表
然后对于小于和大于的链表递归调用
最后把三个组合在一起,返回小于的链表
注意的点(摔过的坑 ):
- 小于的链表要判定是否为空,由于大于的链表放在后面,null不影响链接
- 命名十分接近,要小心是head还是尾巴,这玩意整死我了
- 切割的时候,返回节点node1要把next删掉,不然会有很长的一条冗余数据
- 留个无效的头节点是很好的,可以避免空链表null产生的很多麻烦,但是要记得删
代码
public class Solution {
ListNode cut(ListNode node0){//切割出node0后面一个节点node1,返回切掉的节点
ListNode node1=node0.next;
node0.next=node1.next;
node1.next=null;
return node1;
}
boolean add(ListNode nodetail,ListNode addnode){//只会加不会后移
if(nodetail.next!=null)return false;
nodetail.next=addnode;
return true;
}
public ListNode sortList(ListNode head) {
if(head==null)return head;
if(head.next==null)return head;//空节点和单个节点都直接返回
ListNode tempNode=head;
//ListNode tempNodeNext=head.next;
//头节点,用0占掉,返回的时候记得删
ListNode lessNodeHead=new ListNode(0);
ListNode equalNodeHead=new ListNode(0);
ListNode greaterNodeHead=new ListNode(0);
//当前节点
ListNode lessNode=lessNodeHead;
ListNode equalNode=equalNodeHead;
ListNode greaterNode=greaterNodeHead;
int div=tempNode.val;//分割点
if(add(equalNode,new ListNode(div))){
equalNode=equalNode.next;
}
while(tempNode.next!=null){
// tempNodeNext=tempNode.next;
if(tempNode.next.val==div){
if(add(equalNode,cut(tempNode))){
equalNode=equalNode.next;
}
continue;
}
if(tempNode.next.val<div){
if(add(lessNode,cut(tempNode))){
lessNode=lessNode.next;
}
continue;
}
if(tempNode.next.val>div){
if(add(greaterNode,cut(tempNode))){
greaterNode=greaterNode.next;
}
continue;
}
}
//记得去头
if(lessNodeHead.next==null)lessNodeHead=lessNodeHead.next;
else lessNodeHead=sortList(lessNodeHead.next);
if(greaterNodeHead.next==null)greaterNodeHead=greaterNodeHead.next;
else greaterNodeHead=sortList(greaterNodeHead.next);
equalNodeHead=equalNodeHead.next;
//找尾巴
lessNode=lessNodeHead;
equalNode=equalNodeHead;
greaterNode=greaterNodeHead;
if(lessNode!=null)while(lessNode.next!=null)lessNode=lessNode.next;
if(equalNode!=null)while(equalNode.next!=null)equalNode=equalNode.next;
//组合
equalNode.next=greaterNodeHead;
if(lessNode!=null)lessNode.next=equalNodeHead;
else lessNodeHead=equalNodeHead;
return lessNodeHead;
}
}
想不到怎么优化,而且貌似空间复杂度不是常数···