常见排序算法总结

来源:互联网 发布:高科技软件 编辑:程序博客网 时间:2024/05/20 06:53
package com.ql.Sort;import java.util.ArrayList;//import java.util.LinkedList;import java.util.List;public class Sort {    /**     * insertion sort      * O(N^2)     * @param a     */    public static <AnyType extends Comparable<? super AnyType>>     void insertionSort(AnyType[] a) {          insertionSort(a, 0, a.length - 1);    }    private static <AnyType extends Comparable<? super AnyType>>     void insertionSort(AnyType[] a, int left, int right) {        int j; // 记录第一个比tmp小的元素的后边一位的位置        //for(int p = left;p <= right;p++)        for(int p = left;p < right;p++){            AnyType tmp = a[p];            for(j = p; j > left && tmp.compareTo(a[j - 1]) < 0; j--)                a[j] = a[j - 1];            a[j] = tmp;        }    }    /**     * Shell sort      * O(N^2)     * @param a     */    public static <AnyType extends Comparable<? super AnyType>>    void ShellSort(AnyType [] a){        int j;        //希尔增量        for(int gap = a.length/2;gap > 0;gap /= 2){            for(int i = gap;i < a.length;i++){                AnyType tmp = a[i];                for(j = i;j >= gap && tmp.compareTo(a[j-gap]) < 0;j -= gap){                    a[j] = a[j-gap];                a[j] = tmp;                }            }        }    }    /**     * Heap sort      * 平均O(N^1.3)  不同增量时间复杂度不同     * @param a     */    private static int leftChild(int i){        return 2*i+1;    }    private static <AnyType extends Comparable<? super AnyType>>    void percDown(AnyType [] a,int i,int n){        int child;        AnyType tmp;        for(tmp = a[i];leftChild(i) < n;i =child){            child = leftChild(i);            if(child != n-1 && a[child].compareTo(a[child + 1]) < 0)                child++;            if(tmp.compareTo(a[child]) < 0)                a[i] = a[child];            else                break;        }        a[i] = tmp;    }    private static <AnyType extends Comparable<? super AnyType>>    void swapReferences(AnyType[] a, int i, int j) {        AnyType tmp = a[i];          a[i] = a[j];          a[j] = tmp;    }    public static <AnyType extends Comparable<? super AnyType>>    void HeapSort(AnyType [] a){        for(int i = a.length/2 - 1;i >= 0;i--)            percDown(a, i, a.length);        for(int i = a.length - 1;i > 0;i--){            swapReferences(a,0,i);            percDown(a, 0, i);        }    }    /**     * Merge sort      * O(NlogN)     * @param a     */    public static <AnyType extends Comparable<? super AnyType>>    void MergeSort(AnyType [] a,AnyType [] tmpArray,int left,int right){        if(left < right){            int center = (left + right)/2;            MergeSort(a, tmpArray, left, center);            MergeSort(a, tmpArray, center+1, right);            Merget(a, tmpArray, left, center + 1, right);        }    }    @SuppressWarnings("unchecked")    public static <AnyType extends Comparable<? super AnyType>>    void MergeSort(AnyType [] a){        AnyType [] tmpArray = (AnyType[]) new Comparable[a.length];        MergeSort(a, tmpArray, 0, a.length - 1);    }    public static <AnyType extends Comparable<? super AnyType>>    void Merget(AnyType [] a,AnyType [] tmpArray,int leftPos,int rightPos,int rightEnd){        int leftEnd = rightPos - 1;        int tmpPos = leftPos;        int numElements = rightEnd - leftPos + 1;        while(leftPos <= leftEnd && rightPos <= rightEnd)            if(a[leftPos].compareTo(a[rightPos]) <= 0)                tmpArray[tmpPos++] = a[leftPos++];            else                tmpArray[tmpPos++] = a[rightPos++];        for(int i = 0;i<numElements;i++,rightEnd--)            a[rightEnd] = tmpArray[rightEnd];    }    /**     * Quick sort      * O(NlogN)     * @param a     */    public static void sort(List<Integer> items){        List<Integer> smaller = new ArrayList<>();        List<Integer> same = new ArrayList<>();        List<Integer> larger = new ArrayList<>();        Integer chosenItem = items.get(items.size()/2);        for(Integer i:items){            if(i<chosenItem)                smaller.add(i);            else if(i>chosenItem)                larger.add(i);            else                same.add(i);        }        sort(smaller);        sort(larger);        items.clear();        items.addAll(smaller);        items.addAll(same);        items.addAll(larger);    }/** * @author Administrator *  实际的快排例程 */    private static final int COTOFF = 10;    /**     * Quicksort algorithm     *  驱动程序     */    public static <AnyType extends Comparable<? super AnyType>>    void quicksort(AnyType [] a){        quicksort(a,0,a.length - 1);    }    /**     * Return median of left,center,and right.     * Order these and hide the pivot     *  执行三只分割法的程序     * @return      */    public static <AnyType extends Comparable<? super AnyType>>    AnyType media3(AnyType [] a,int left,int right){        int center = (left + right) / 2;        if(a[center].compareTo(a[left]) < 0)            swapReferences(a,left,center);        if(a[right].compareTo(a[left]) < 0)            swapReferences(a,left,right);        if(a[right].compareTo(a[center]) < 0)            swapReferences(a,center,right);        swapReferences(a,center,right-1);        return a[right-1];    }    /**     * Internal quicksort method that makes recursive calls     * Uses median-of-three partitioning and a cutoff of 10     *  快排的主例程     */    private static <AnyType extends Comparable<? super AnyType>>    void quicksort(AnyType [] a,int left,int right){        if(left + COTOFF <= right){            AnyType pivot = media3(a,left,right);            /*int i = left,j = right - 1;            for( ; ; ){                while(a[++i].compareTo(pivot)<0){ }                while(a[--j].compareTo(pivot)<0){ }                if(i<j)                    swapReferences(a, i, j);                else                    break;            }*/            //对快排小的改动,它将中断该算法            int i = left + 1,j = right - 2;            for( ; ; ){                while(a[i].compareTo(pivot)<0) i++;                while(a[j].compareTo(pivot)<0) j--;                if(i<j)                    swapReferences(a, i, j);                else                    break;            }            swapReferences(a, i, right - 1);            quicksort(a,left,i-1);            quicksort(a,i+1,right);        }        else            insertionSort(a,left,right);    }    /**     * Internal selection method that makes recursive calls     * Uses median-of-three partitioning and a cutoff of 10     *  快速选择的主例程     */    @SuppressWarnings("unused")    private static <AnyType extends Comparable<? super AnyType>>    void quickSelect(AnyType [] a,int left,int right,int k){        if(left + COTOFF <= right){            AnyType pivot = media3(a,left,right);            int i = left,j = right - 1;            for( ; ; ){                while(a[++i].compareTo(pivot)<0){ }                while(a[--j].compareTo(pivot)<0){ }                if(i<j)                    swapReferences(a, i, j);                else                    break;            }            swapReferences(a, i, right - 1);            if(k <= i)                quickSelect(a, left, i - 1, k);            else if(k > i+1)                quickSelect(a, i + 1, right, k);        }        else            insertionSort(a,left,right);    }    /**     * Radix sort      * 最坏情况下O(NlogN)  特殊情况下线性排序还是可能的     * @param a     */    @SuppressWarnings("unchecked")    public static void radixSortA(String [] arr,int stringLen){        final int BUCKETS = 256;        ArrayList<String> [] buckets = new ArrayList[BUCKETS];        for(int i = 0;i < BUCKETS; i++)            buckets[i] = new ArrayList<>();        for(int pos = stringLen - 1;pos >= 0;pos-- ){            for(String s:arr)                buckets[s.charAt(pos)].add(s);            int idx = 0;            for(ArrayList<String> thisBucket : buckets){                for(String s:thisBucket)                    arr[idx++] = s;                thisBucket.clear();            }        }    }    //定长字符串的计数基数排序    public static void countingradixSort(String [] arr,int stringLen){        final int BUCKETS = 256;        int N = arr.length;        String [] buffer = new String [N];        String [] in = arr;        String [] out = buffer;        for(int pos = stringLen - 1;pos >= 0;pos--){            int [] count = new int [BUCKETS + 1];            for(int i = 0;i < N;i++)                count[in[i].charAt(pos)+1]++;            for(int b = 1;b <= BUCKETS;b++)                count[b] += count[b - 1];            for(int i = 0;i < N; i++)                out[count[in[i].charAt(pos)]++] = in[i];            //Swap in and out roles            String [] tmp = in;            in = out;            out= tmp;        }        if(stringLen % 2 == 1)            for(int i = 0;i < arr.length;i++)                out[i] = in[i];    }    //变长字符串的基数排序    public static void radixSort(String [] arr,int maxLen){        final int BUCKETS = 256;        ArrayList<String> [] wordsByLength = new ArrayList[maxLen + 1];        ArrayList<String> [] buckets = new ArrayList[BUCKETS];        for(int i = 0;i < wordsByLength.length; i++)            wordsByLength[i] = new ArrayList<>();        for(int i = 0;i < BUCKETS; i++)            buckets[i] = new ArrayList<>();        for(String s:arr)            wordsByLength[s.length()].add(s);        int idx = 0;        for(ArrayList<String> wordlist : wordsByLength){            for(String s:wordlist)                arr[idx++] = s;        int startingIndex = arr.length;        for(int pos = maxLen - 1;pos >= 0;pos--){            startingIndex -= wordsByLength[pos+1].size();            for(int i = startingIndex;i < arr.length;i++)                buckets[arr[i].charAt(pos)].add(arr[i]);            idx=startingIndex;            for(ArrayList<String> thisBucket:buckets){                for(String s:thisBucket)                    arr[idx++] = s;                thisBucket.clear();            }        }    }       }}
0 0