常见排序之Java实现

来源:互联网 发布:手机运行linux arm 编辑:程序博客网 时间:2024/06/03 17:32

主程序

public class Test {    public static void main(String[] args) {        int[] arrs = {1, 9, 4, 50, 63, 82, 37} ;        System.out.println(Arrays.toString(arrs)) ;        //mergeSort(arrs, 0, arrs.length-1) ;            //quickSort(arrs, 0, arrs.length - 1) ;        heapSort(arrs) ;        System.out.println(Arrays.toString(arrs)) ;    }}

交换数组中的两个元素

    private static void swap(int[] array, int low, int high) {        int temp = array[low] ;        array[low] = array[high] ;        array[high] = temp ;    }

插入排序

    public static void insertSort(int[] arr) {        int key ;   //用于保存要插入的值        for(int i=1 ; i<=arr.length-1 ; i++) {            key = arr[i] ;            for(int j=i-1 ; j>=0 ; j--) {                if(key < arr[j]) {                    arr[j+1]=arr[j] ;   //记录后移                }                else {                    arr[j+1] = key ;    //找到插入的位置                    break ;                }            }        }    }

选择排序(当前元素 VS 余下元素)

    public static void selectSort(int[] arr) {        for(int i=0; i<=arr.length-2; i++) {            for(int j=i+1; j<=arr.length-1; j++) {                if(arr[i] > arr[j]) {                    swap(arr, i, j) ;                }            }        }    }

冒泡排序(两两比较)

    public static void bubbleSort(int[] arr) {        for(int i=arr.length-1; i>=1; i--) {            for(int j=0; j<=i-1; j++) {                if(arr[j] > arr[j+1]) {                    swap(arr, j, j+1) ;                }            }        }    }

二路归并排序(递归版本)

    public static void mergeSort(int[] arr, int low, int high) {        if(low < high) {            int mid = (low+high) / 2 ;            mergeSort(arr, low, mid) ;            mergeSort(arr, mid+1, high) ;            merge(arr, low, mid, high) ;        }    }    public static void merge(int[] arr, int left, int center, int right) {        int[] temp = new int[right-left+1] ;    //归并排序的空间复杂度为O(n)        int k = 0 ;        int r1 = center+1 ;     //右边起始下标        int start = left ;      //保存拷贝的起始位置        while(left<=center && r1<=right) {            if(arr[left] < arr[r1]) { temp[k++] = arr[left++] ; }            else { temp[k++] = arr[r1++] ; }        }        //拷贝剩余元素        while(left <= center) { temp[k++] = arr[left++] ; }        while(r1 <= right) { temp[k++] = arr[r1++] ; }        //将临时数组中的元素拷贝至原数组        k = 0 ;        for(int i=start; i<=right ; i++) { arr[i] = temp[k++] ; }    }

二路归并排序(非递归版本)

    public static void mergeSort(int[] arr) {        int length = arr.length ;        int low, mid, high ;        for(int step = 1 ; step <= length; step*=2) {   //step为步长            low = 0 ;            while(low+step <= length) {                mid = low + step - 1 ;                high = mid + step ;                if(high >= length) { high = length - 1 ; }      //元素个数小于step                merge(arr, low, mid, high);                low = high + 1 ;    //下次归并的下界            }        }    }    public static void merge(int[] arr, int left, int center, int right) {        int[] temp = new int[right-left+1] ;    //归并排序的空间复杂度为O(n)        int k = 0 ;        int r1 = center+1 ;     //右边起始下标        int start = left ;      //保存拷贝的起始位置        while(left<=center && r1<=right) {            if(arr[left] < arr[r1]) { temp[k++] = arr[left++] ; }            else { temp[k++] = arr[r1++] ; }        }        //拷贝剩余元素        while(left <= center) { temp[k++] = arr[left++] ; }        while(r1 <= right) { temp[k++] = arr[r1++] ; }        //将临时数组中的元素拷贝至原数组        k = 0 ;        for(int i=start; i<=right ; i++) { arr[i] = temp[k++] ; }    }

快速排序(递归版本)

    public static void quickSort(int[] array, int low, int high) {        if(low < high) {            int i = partition(array, low, high) ;            quickSort(array, low, i-1);            quickSort(array, i+1, high);        }    }    private static int partition(int[] array, int low, int high) {        int pivot = array[low] ;        while(low < high) {            while(low < high && pivot <= array[high]) { high-- ; }            swap(array, low, high) ;            while(low < high && pivot >= array[low]) { low++ ; }            swap(array, low, high) ;        }        return low ;    }

快速排序(非递归版本)

    public static void quickSort(int[] array) {        if(array==null || array.length==1) { return ; }        //保存划分后所形成空间的左右端点        Stack<Integer> stack = new Stack<Integer>() ;        stack.push(0) ;        stack.push(array.length - 1) ;        int low, high ;        while(! stack.isEmpty()) {            high = stack.pop() ;            low = stack.pop() ;            if(low >= high) { continue ; }            int i = partition(array, low, high) ;            stack.push(low) ;   //保存左边的区间            stack.push(i-1) ;            stack.push(i+1) ;   //保存右边的区间            stack.push(high) ;        }    }    private static int partition(int[] array, int low, int high) {        int pivot = array[low] ;        while(low < high) {            while(low < high && pivot <= array[high]) { high-- ; }            swap(array, low, high) ;            while(low < high && pivot >= array[low]) { low++ ; }            swap(array, low, high) ;        }        return low ;    }

堆排序

    public static void heapSort(int[] heap) {        buildHeap(heap) ;   //构建堆        for(int size=heap.length-1 ; size >= 1 ; ) {            swap(heap, 0, size);    //交换首末元素            adjustHeap(heap, --size, 0);  //对剩余元素进行调整        }    }    public static void buildHeap(int[] heap) {        int size = heap.length-1 ;        //自底向上调整堆        for(int begin = size/2 ; begin>=0 ; begin--){            adjustHeap(heap, size, begin) ;        }    }    public static void adjustHeap(int[] heap, int size, int start) {        int big = start ;   //保存较大元素下标        int left = 2*start + 1 ;    //左叶子节点        int right = 2*start + 2 ;   //右叶子节点        while(left<=size || right<=size) {            if(left<=size && heap[left]>heap[big]) { big=left ; }            if(right<=size && heap[right]>heap[big]) { big=right ; }            if(start == big) {  break ; }   //调整完毕            else {                swap(heap, start, big) ;    //较大元素上浮                start = big ;                left = 2*start + 1 ;                right = 2*start + 2 ;            }        }    }