連結串列排序演算法java實現(連結串列的快速排序、插入排序、歸併排序)
阿新 • • 發佈:2018-12-13
難易程度:★★
重要性:★★★
連結串列的排序相對陣列的排序更為複雜些,也是考察求職者是否真正理解了排序演算法(而不是“死記硬背”)
-
連結串列的插入排序
public class LinkedInsertSort { static class ListNode { int val; ListNode next; ListNode(int x) { val = x; next = null; } } public static ListNode insertionSortList(ListNode head) { if(head==null||head.next==null) return head; ListNode pre = head;//pre指向已經有序的節點 ListNode cur = head.next;//cur指向待排序的節點 ListNode aux = new ListNode(-1);//輔助節點 aux.next = head; while(cur!=null){ if(cur.val<pre.val){ //先把cur節點從當前連結串列中刪除,然後再把cur節點插入到合適位置 pre.next = cur.next; //從前往後找到l2.val>cur.val,然後把cur節點插入到l1和l2之間 ListNode l1 = aux; ListNode l2 = aux.next; while(cur.val>l2.val){ l1 = l2; l2 = l2.next; } //把cur節點插入到l1和l2之間 l1.next = cur; cur.next = l2;//插入合適位置 cur = pre.next;//指向下一個待處理節點 }else{ pre = cur; cur = cur.next; } } return aux.next; } }
- 連結串列的快速排序
public static ListNode quickSort(ListNode begin, ListNode end) { //判斷為空,判斷是不是隻有一個節點 if (begin == null || end == null || begin == end) return begin; //從第一個節點和第一個節點的後面一個幾點 //begin指向的是當前遍歷到的最後一個<= nMidValue的節點 ListNode first = begin; ListNode second = begin.next; int nMidValue = begin.val; //結束條件,second到最後了 while (second != end.next && second != null) {//結束條件 //一直往後尋找<=nMidValue的節點,然後與fir的後繼節點交換 if (second.val < nMidValue) { first = first.next; //判斷一下,避免後面的數比第一個數小,不用換的局面 if (first != second) { int temp = first.val; first.val = second.val; second.val = temp; } } second = second.next; } //判斷,有些情況是不用換的,提升效能 if (begin != first) { int temp = begin.val; begin.val = first.val; first.val = temp; } //前部分遞迴 quickSort(begin, first); //後部分遞迴 quickSort(first.next, end); return begin; }
-
連結串列的歸併排序
public ListNode mergeSort(ListNode head){ if(head==null || head.next==null) return head; ListNode mid = getMid(head);//獲取連結串列中間節點 //把連結串列從之間拆分為兩個連結串列:head和second兩個子連結串列 ListNode second = mid.next; mid.next = null; //對兩個子連結串列排序 ListNode left = mergeSort(head); ListNode right = mergeSort(second); return merge(right,left); } //兩個有序連結串列的歸併 private ListNode merge(ListNode l1,ListNode l2){ //輔助節點,排好序的節點將會連結到dummy後面 ListNode dummy = new ListNode(0); ListNode tail = dummy;//tail指向最後一個排好序的節點 while(l1!=null&&l2!=null){ if(l1.val<=l2.val){ tail.next = l1; l1 = l1.next; }else{ tail.next = l2; l2 = l2.next; } tail = tail.next; //移動tail指標 } if(l1!=null) tail.next = l1; else tail.next = l2; return dummy.next; } //返回連結串列之間節點 private ListNode getMid(ListNode head){ if(head==null ||head.next==null) return head; ListNode slow = head; ListNode faster = head.next; while(faster!=null&&faster.next!=null){ slow = slow.next; faster = faster.next.next; } return slow; }
轉自來自微信公眾號,一個專注應屆生網際網路求職分享的公眾號,公眾號ID:“菜鳥名企夢”