五中基础排序算法实现细节

由于时间仓促,本文先展示实现代码,后续抽空进行思路的补充。

class Solution {
public:
    /**
     * @param A: an integer array
     * @return: nothing
     */
    void sortIntegers(vector<int> &A) {
        // write your code here
        mergeSort(A,0,A.size()-1);
    }

private:
    void bubbleSort(std::vector<int> &A);
    void bubbleSort_2(std::vector<int> &A);
    void selectSort(std::vector<int> &A);
    void insertSort(std::vector<int> &A);
    void quickSort(std::vector<int> &A,int left,int right);
    void mergeSort(std::vector<int> &A,int left,int right);
static int partition(std::vector<int> &A,int left,int right);
static void merge(std::vector<int> &A,int l1,int r1,int l2,int r2);
};

void Solution::bubbleSort(std::vector<int> &A){
    int len=A.size();
    for(int i=0;i<len-1;i++)
        for(int j=0;j<len-1-j;j++)
            if(A[j]>A[j+1])
                swap(A[j],A[j+1]);
}


void Solution::bubbleSort_2(std::vector<int> &A){
    int len=A.size();
    int sorted=false;   //添加标志位,减少遍历次数
    for(int i=0;i<len-1;i++){
        if(sorted)
            return;
        sorted=true;
        for(int j=0;j<len-1-i;j++){
            if(A[j]>A[j+1]){
                swap(A[j],A[j+1]);
                sorted=false;
            }
        }
    }
}
//冒泡相邻比较,可能一轮中交换多次,选择是拿出最小的,交换一次
void Solution::selectSort(std::vector<int> &A){
    //选择排序每次选择在没有排序的队列中选择最小的那个数放到已经排序的队列后面
    //无论如何,它每次都会比较剩余的所有的数,所以时间复杂度最坏最好平均都是O(n2),但是不稳定
    int len=A.size();
    for(int i=0;i<len-1;i++){   //每一轮保证位置i上是未排序中的最小的
        int min=i;
        for(int j=i+1;j<len;j++)//每次都是假定i最小,比较i之后的数,所以时间复杂度不变
            if(A[j]<A[min])
                min=j;
        swap(A[i],A[min]);
    }
}

void Solution::insertSort(std::vector<int> &A){
    //插入排序:每次把未排序的头部插入到已经排序的队列中(关键找到不小于他的数字)
    //只要比待插入数字大,则往后移动一下,直到小于或者等于这个数字为止,也稳定
    int len=A.size();
    for(int i=1;i<len;i++){     //i代表每次需要插入的元素位置。
        int j=i-1;
        int tmp=A[i-1];
        for(;j>=0;j--)
            if(A[j]>tmp){   //比该元素大的统统往后移动一个。
                A[j+1]=A[j];
                continue;
            }
            else
                break;
        A[j+1]=tmp; //最后把待排序元素插入即可,这个位置一定可以放
    }
}

//分治思想,将这个划分成两个部分,并且返回基准的位置
int Solution::partition(std::vector<int> &A,int left,int right){
    int pivot=A[left];
    int i=left,j=right;
    while(i<j){
        while(A[j]>=pivot && j>i)
            j--;
        while(A[i]<=pivot && i<j)
            i++;
        swap(A[i],A[j]);
    }
    swap(A[left],A[i]);
    return i;
}

//快速排序,不稳定排序。
void Solution::quickSort(std::vector<int> &A,int left,int right){
    if(left>=right)
        return ;
    int pivot_index=partition(A,left,right);
    quickSort(A,left,pivot_index-1);
    quickSort(A,pivot_index+1,right);
}

//归并排序
void Solution::mergeSort(std::vector<int> &A,int left,int right){
    if(left>=right)
        return ;
    int mid=(left+right)/2;
    mergeSort(A,left,mid);
    mergeSort(A,mid+1,right);
    merge(A,left,mid,mid+1,right);
}

void Solution::merge(std::vector<int> &A,int l1,int r1,int l2,int r2){
    vector<int> tmp;
    int i=l1;
    int j=l2;
    while(i<=r1 && j<=r2){
        if(A[i]<=A[j]){
            tmp.push_back(A[i]);
            i++;
        }
        else{
            tmp.push_back(A[j]);
            j++;
        }
    }
    while(i<=r1){
        tmp.push_back(A[i]);
        i++;
    }
    while(j<=r2){
        tmp.push_back(A[j]);
        j++;
    }
    for(int k=l1;k<=r2;k++){
        A[k]=tmp[k-l1];
    }
}

猜你喜欢

转载自blog.csdn.net/nwpubear/article/details/81543642