1. 程式人生 > >java演算法-分治演算法排序

java演算法-分治演算法排序

package suanfa.sort;



/**
分治演算法
原理:兩組撲克牌,假設都是排序好的,小牌在上面,那這兩個排序就比較最上面的兩張,吧其中最小的放到第三組,作為結果,直到兩組牌其中一組全部取完,另一組剩下的放到第三組
分兩個方法
分解方法:將陣列二分為兩個陣列,然後各自一半繼續拆分為兩個陣列,直到無法拆分(最後一組稱為葉子),樹狀結構
歸約方法:從最葉子吧兩個數組合併為一個數組
經過測試 10萬長度的陣列需要 100毫秒 ,比插入排序快80倍,長度越大,差距越明顯
 */
public class FenZhiSort {
    public static void main
(String[] args) { // System.out.println(Arrays.toString(merge(new int[]{1,3,8,9}, new int[]{2,4,5,6,7,10}))); // // // Node n = new Node(new int[]{3,6,1,4,2,100,99,89,56,32,11,10}); // n.sort(); // System.out.println(Arrays.toString(n.arr)); int[] arr = new int[100000]; for
(int i=0;i<arr.length;i++){ arr[i] = arr.length - i; } long start = System.currentTimeMillis(); Node n = new Node(arr); n.sort(); //System.out.println(Arrays.toString(n.arr)); System.out.println("耗時:"+(System.currentTimeMillis()-start)); } public
static class Node{ int[] arr; boolean isSort = false; Node left; Node right; public Node(int[] arr){ this.arr = arr; } public void sort(){ fenjie(this); sort(this); } public void sort(Node n){ if(n == null || n.isSort){ return; } if(n.left == null && n.right == null){ return; }else if(n.left != null && n.right == null){ if(n.left.isSort){ n.arr = n.left.arr; n.isSort = true; return; }else{ sort(n.left); } }else if(n.left == null && n.right != null){ if(n.right.isSort){ n.arr = n.right.arr; n.isSort = true; return; }else{ sort(n.right); } }else{ if(!n.right.isSort){ sort(n.right); } if(!n.left.isSort){ sort(n.left); } n.arr = merge(n.left.arr, n.right.arr); n.isSort = true; } } public void fenjie(Node n){ if(n.arr == null || n.arr.length == 0){ return; } if(n.arr.length == 1){ n.left = new Node(n.arr); n.left.isSort = true; n.arr = null; }else if(n.arr.length == 2){ n.left = new Node(new int[]{n.arr[0]}); n.left.isSort = true; n.right = new Node(new int[]{n.arr[1]}); n.right.isSort = true; n.arr = null; }else if(n.arr.length%2==0){ n.left = new Node(new int[n.arr.length/2]); n.right = new Node(new int[n.arr.length/2]); for(int i=0;i<n.arr.length/2;i++){ n.left.arr[i] = n.arr[i]; n.right.arr[i] = n.arr[n.arr.length-i-1]; } fenjie(n.left); fenjie(n.right); n.arr = null; }else{ n.left = new Node(new int[n.arr.length/2+1]); n.right = new Node(new int[n.arr.length/2]); for(int i=0;i<n.arr.length/2+1;i++){ n.left.arr[i] = n.arr[i]; if(i != n.arr.length-i-1){ n.right.arr[i] = n.arr[n.arr.length-i-1]; } } fenjie(n.left); fenjie(n.right); } } } public static int[] merge(int[] arr1,int[] arr2){ int[] arr3 = new int[arr1.length+arr2.length]; int i=0; int i1=0; int i2=0; while(true){ if(!hasNext(arr1,i1)){ for(int k=i2;k<arr2.length;k++){ arr3[i++] = arr2[k]; } break; }else if(!hasNext(arr2,i2)){ for(int k=i1;k<arr1.length;k++){ arr3[i++] = arr1[k]; } break; }else if(arr1[i1]>arr2[i2]){ arr3[i++] = arr2[i2++]; }else{ arr3[i++] = arr1[i1++]; } } return arr3; } public static boolean hasNext(int[] arr,int i){ return i<=arr.length-1; } }