Detailed essential sorting algorithms (java code implementation, illustration and comparison, continuously updated)

Reference article: HTTPS: //blog.csdn.net/hellozhxy/article/details/79911867
(compare sort of) https://blog.csdn.net/mengyue000/article/details/77505666

the term

Stability: If a had in front of b, b and a front still after a = b, sorting;
instability: If a b originally in front, and a = b, after ordering a b may appear in the back;
the sort: Sort all operations are done in memory;
external sorting: Since the data is too large, so the data on the disk, and disk and memory by sorting data before transmission;
time complexity: execute an algorithm takes to time.
Space complexity: End of a desired size to run memory-intensive programs.

Here Insert Picture Description
Annotations: In-place: constant memory occupy, without occupying additional memory
Out-place: uses extra memory

Sort and compare the difference between non-comparative

  1. Compare Sort by:
  • Common: quick sort, merge sort, heap sort, bubble sort, etc. In the process of sorting, the order between the elements depends on the comparison between the elements, each number must be sorting algorithms compare with other numbers.
  • Features: For data of all sizes, do not care about the distribution of data to compare one size fits all
  1. Non-comparative Sort:
  • Common: counting algorithm to sort by determining the number of elements in front of each sorting element, radix sort, barrels and the like shot sequence.
  • Features: Only the front element to determine the number of each element, you can traverse once solved, but due to the need to determine a unique position to take up space, so the data size and data distribution has certain requirements.

1. Bubble Sort

  1. Ideas:
    The first step: starting with the first element, after comparing adjacent elements to determine whether the exchange until the last element.
    The second step: Repeat step for all elements down through the exchange does not appear in the end of the sort.

  2. Performance Analysis:
    time complexity:
    2.1 best case:. O (n-)
    . Average 2.2 where: O (n-^ 2)
    2.3 worst case:. O (n ^ 2)
    space complexity: O (1)
    Stability : stable (the same relative position of elements does not change)

  3. Applicable scene

  • Fewer cases applicable element, the element too much, the exchange and the number of comparisons will be much, affect the efficiency, elements and more cases suitable for quick sort.
  • When the substantially ordered array using bubble sort, and the case for direct insertion sort, rank them in order to substantially close the case time complexity of O (n).
  1. Graphic:
    Here Insert Picture Description

  2. Code

  int [] bubbleSort(int [] data){
        int flag=0;
        int temp=0;
        for (int i = 0; i <data.length ; i++) {
            flag=0;
            for (int j = 0; j <data.length-i-1 ; j++) {
                if(data[j]>data[j+1]){
                   temp =data[j];
                   data[j]=data[j+1];
                   data[j+1]=temp;
                   flag=1;
                }
            }
            if (flag==0){
                break;
            }
        }
        return data;
    }

Insertion Sort

  1. Ideas: Landlords like when finishing hand, step by step, the lowest card on the far left, it works by constructing an ordered sequence, for unsorted data, scanned from back to front in the sorted sequence, found and insert the corresponding position. In the realization of insertion sort, sort commonly used in-place (i.e., only need to use the sort of extra space O (1)), and therefore in the forward scan from the process, the need to repeatedly sorted elements gradually move rearward position , the latest element inserted into the space provided.

  2. Performance Analysis:
    best case: T (n) = O ( n)
    worst case: T (n) = O ( n2)
    Average where: T (n) = O ( n2)
    space complexity: O (1)
    stable : the stability (the same relative position of elements does not change)

  3. Application: suitable for a smaller number of sort.

  4. Features: the same stability sorting algorithm, time complexity is the same, better than the efficiency of insertion sort bubble sort, especially when large amount of data, bubble sort operation of the mobile data more, as long as the element is less than a, We will once again traverse. So its low efficiency. (generally)

  5. Diagram
    Here Insert Picture Description

  6. achieve

//由于是从第一个元素开始比较,可以知道current前面都是有序递增的,注意后移要从最后开始
    int [] insertSort(int[] target){
        int temp;
        int current=0;
        for (int i = 1; i <target.length ; i++) {
            temp=target[i];
            current=i-1;
            while(current>=0&&temp<target[current]){
                target[current+1]=target[current];
                current--;
            }
            target[current+1]=temp;
        }
        return target;
    }

Selection Sort

  1. Ideas: in the choice of ordering, not only two adjacent data comparison. It is necessary to record the data of a particular index, choose to sort all the data is scanned again, pick out (in ascending order) a minimum of data, the minimum data and index data leftmost 0 exchange position. After the scan data again from the beginning at index 1, or pick out the smallest number 1 position and then exchanged, this process continues until all the data are scheduled. The need for a program identifier to identify each variable pick the smallest index data.

  2. Features: Selection Sort improved bubble sort, the necessary number of exchanges reduced from O (N2) to O (N) time. Unfortunately, the number of comparisons remain as O (N2). However, selection sort still made a very important improvement to sort large amounts of records, because they need to move a large number of records in memory, which makes time and time comparisons exchange comparison, switching time is more important . (In general, the Java language is not the case, just change the references to Java in position, and the position of the real object does not change.)

  3. Performance Analysis:
    2.4 Algorithm Analysis
    best case: T (n) = O ( n2)
    worst case: T (n) = O ( n2)
    Average where: T (n) = O ( n2)
    stability: stable.

  4. Diagram

Here Insert Picture Description

  1. achieve:
int [] selectSort(int [] target){
        int current;
        int temp;
        for (int i = 0; i <target.length ; i++) {
            current=i;
            for (int j = i; j <target.length ; j++) {
                if(target[current]>target[j]){
                    current=j;
                }
            }
            temp=target[current];
            target[current]=target[i];
            target[i]=temp;
        }
        return target;
    }

Reference article: https: //blog.csdn.net/u013249965/article/details/52575324

4. Comparison of three basic algorithms

Unless it does not have the algorithm can refer to, in general, almost impossible to use bubble sort algorithm. It is too simple, so you can effortlessly write it down. However, when a small amount of data when it will be some application value.

Selection Sort Although the number of exchanges to a minimum, but the number is still relatively large. When the small amount of data, and data exchange with respect to the case where the comparison data is more time-consuming, can be applied to select the sorting.

In most cases, it is assumed when a small amount of data or substantially when ordered, insertion sort three simple sorting algorithm is the best choice. For ordering a larger amount of data, the quick sort is usually the fastest way: will be introduced later.

Reference article: https: //blog.csdn.net/morewindows/article/details/6684558

5. Quick Sort

  1. Ideas: The basic idea of ​​this method is:
  • Taken as a reference number of a start number in the number of columns.

  • Partitioning process, than the large full-count put it right, it is less than or equal to the number of full-put it on the left.

  • And then the second step is repeated around the interval, until each section is only a number.

  1. Performance:
    best case: T (n) = O ( nlogn)
    worst case: T (n) = O ( n2)
    Average where: T (n) = O ( nlogn)
    Stability: Unstable

  2. Features: divide and conquer, very fast, but it is unstable and not suitable for sorting objects, I used here is the first number as the reference number, so do not try to apply the actual situation.

  3. Diagram
    Here Insert Picture Description

  4. achieve

  void quickSort(int[] target,int min,int max){
       if(max>min){
           int i=min,j=max;
           int x=target[min];
           //保存基准数后,找到最后的位置,将参照数放到指定位置上就行。
           while(i<j){
               while (i<j&&target[j]>=x){
                   j--;
               }
               target[i]=target[j];
               while(i<j&&target[i]<=x){
                   i++;
               }
               target[j]=target[i];
           }
           target[i]=x;
           quickSort(target,i+1,max);
           quickSort(target,min,i-1);

       }
    }

Reference article: https: //blog.csdn.net/MoreWindows/article/details/6678165#commentBox

Merge sort

  1. Ideas: sorting and selecting like merge sort of performance affected by the input data, but the performance is much better than selection sort, because always is O (n log n) time complexity. The cost of additional memory space is needed.

  2. Diagram
    Here Insert Picture Description

  3. Features: also a sub-ideology rule of law, faster, inferior to quick sort, secondary storage is a big drawback, but stable sorting algorithm for sorting objects.

  4. Performance:
    best case: T (n) = O ( n)
    worst case: T (n) = O ( nlogn)
    Average where: T (n) = O ( nlogn)
    Stability: Stable
    .

  5. achieve

  void mergeSort(int [] target){
        int [] temp=new int[target.length];
        mergeSort(target,0,target.length-1,temp);
    }
    
    void mergeSort(int []target, int left,int right,int[] temp){
        if(left<right){
            int mid=left+(right-left)/2;
            mergeSort(target,left,mid,temp);
            mergeSort(target,mid+1,right,temp);
            mergeSort(target,left,mid,right,temp);
        }
    }
    
    //合并两个数组的操作
    void mergeSort(int []target, int left,int mid,int right,int[] temp){
        int k=0;

		//两个数组的第一个值    
        int left_frist=left;
        int right_frist=mid+1;

        while (left_frist<=mid&&right_frist<=right){
            if(target[left_frist]>target[right_frist]){
            
                temp[k++]=target[right_frist++];
            }else {

                temp[k++]=target[left_frist++];
            }
        }
        //一个合并好,另外一个还没有
        while (left_frist<=mid){
            temp[k++]=target[left_frist++];
        }

        while (right_frist<right){
            temp[k++]=target[right_frist++];
        }


        //最后改变target数组,记得是改变left开头的
        for (int i = 0; i < k; i++)
            target[left+ i] = temp[i];
    }
  1. Related issues merging algorithm:
    1) Find the array reverse order, in front of a digital number greater than the latter, the two numbers form a reverse pair.
  • For example: There 1,2,3,4,5,6,7,0 array (1,0); (2.0). . . Seven reverse right.

  • Ideas, when merge sort, the time before and after the two parts are combined already sorted, we start to the mid and end in the mid + 1, wherein if a number less than the second half of the front, the front of the array is less than start_frist all numbers to mid + 1, the count + = mid + 1-start-frist.

public class Solution {
    int count=0;
    
    public int InversePairs(int [] array) {
        int [] temp=new int[array.length];
        getCount(array,0,array.length-1,temp);
        return count%1000000007;
    }

    void getCount(int [] array,int start,int end,int [] temp){
        if(start<end){
            int mid=(end-start)/2+start;
            getCount(array,start,mid,temp);
            getCount(array,mid+1,end,temp);
            getCount(array,start,mid,end,temp);
        }
    }

    void getCount(int [] array, int start, int mid,int end,int [] temp){
        int k=0;
        int start_frist=start;
        int end_frist=mid+1;
        while(start_frist<=mid&&end_frist<=end){
            if(array[start_frist]<array[end_frist]){
                temp[k++]=array[start_frist++];
            }
            else{
                if(count>=1000000007)//数值过大求余
                {
                    count%=1000000007;
                }
                //一旦小于,则代表start_Frist到mid部分都大于end_frist这个值,所以全部要加上去,再加上我的前部分是包括mid,所以要先mid+1再减区start_frist
                
                count+=(mid+1-start_frist);
                temp[k++]=array[end_frist++];
            }
        }

        while(start_frist<=mid){
            temp[k++]=array[start_frist++];
        }
        while(end_frist<=end){
            temp[k++]=array[end_frist++];
        }
        for(int i=0;i<k;i++){
            array[i+start]=temp[i];
        }
    }
    
      
}

Heapsort

Reference article: https: //www.cnblogs.com/Java3y/p/8639937.html

  1. Definition: A Ranking stack using such a data structure designed algorithm, similar to the accumulation of a complete binary tree structure, properties and satisfy deposited: key or index that is a child node is always less than its parent.

  2. Thinking about:
    1) the initial sort key string is constructed to be large top stack, the stack of the initial disordered region;
    2) the top of the stack and the last element of a switching element, this time to obtain the new disordered region R (1 ... n-1) andNew sequenced region R (n), Satisfying R & lt [1,2, ... n--. 1] <= R & lt [n-]
    . 3) due to the new top of the stack R (1) the nature of the exchange may violate the stack, so the need for this disordered region R (1 ... n-1) adapts to the new stack,

  3. image
    Here Insert Picture Description

  4. Code

    //开始建堆,使当前堆的最大值在堆顶
    static void heapsort(int [] target ){
        int size=target.length-1;
        //第一次建堆,使整个数组为一个未排序的堆
        fristheap(target);
        size--;

        for (int i = 0; i <target.length-1 ; i++) {
            swap(target,0,size+1);
            heapify(target,0,size);
            size--;
        }

    }

    //第一次建堆,找出最大值,并使整个树作为一个标准的大顶堆,但是未排序
    static void fristheap(int [] target ){
        //首先从最右子树非叶子节点开始,减1是因为下标从0开始
        int flag=target.length/2-1;
        //记得是直到0的
        for (int i=flag; i >=0 ; i--) {
            heapify(target,i,target.length-1);
        }
    }

    //对以该节点为根的树进行建堆,使最大的max在最上面,
    // 因为我们是从下到上排序子树的,所以不需要考虑子树的子树是否还未排序
    static void heapify(int [] target,int curr,int size){

        //如果当前节点大于数组长度,则没有子节点,该节点必然是最大值
        if(curr<size){
            //注意下标是从0开始的,记得多加一个1
            int left=curr*2+1;
            int right=curr*2+2;
            //首先假设curr是最大值
            int max=curr;
            if(left<size){
                if(target[left]>target[max]){
                    max=left;
                }
            }
            if (right<size){
                if(target[right]>target[max]){
                    max=right;
                }
            }
            if(max!=curr){
                //如果不同则交换值
                swap(target,max,curr);
                //因为max节点值变了,所以以该节点为根的树也同时改变
                heapify(target,max,size);
            }
        }
    }

    static void swap(int [] target,int i,int j){
        int temp=target[i];
        target[i]=target[j];
        target[j]=temp;
    }
Published 36 original articles · won praise 11 · views 10000 +

Guess you like

Origin blog.csdn.net/s_xchenzejian/article/details/98077573