排序--选排,插排,快排

/*
 *
 * 排序方法的分类:
 * 1.按存储介质: 内部排序和外部排序
 *              内存和外存
 * 2.比较器个数: 串行排序和并行排序
 *              单处理器和多处理器
 * 3.主要操作: 比较排序和基数排序
 *             比较方式  非比较方式
 * 4.辅助空间: 原地排序和非原地排序
 *             原地排序:不需要额外的辅助空间.空间复杂度O(1)
 * 5.稳定性: 稳定排序和非稳定排序
 *          稳定排序: 任何数值相等的元素,排序后相对次序不变
 *          for example: 22  34   24   57   39    24'   98
 *          排序后: 22   24    24'   34    39      57    98
 *          应用于元素有多个数据域的情况:
 *          对某东上的某类商品:数据域有 价格,销量,评价......
 *          (1)对销量从高到低排序
 *          (2)对价格由高到低排序
 *          (3)在价格相同情况下,销量高的会排在最前面,不会打乱原来的相对次序
 * 6.自然性: 自然排序和非自然排序
 *          自然排序: 输入数据越有序,排序速度越快
 * */




#include<cstdlib>
#include<iostream>
#include<algorithm>

using namespace std;
void show(int*a,int j,int n);
void show(int *p, int j);

int n;
/*
 * 直接插入排序:
 * 将一个记录插入到已排好的有序序列中,得到一个新的有序表。
 * 将序列的第一个记录看作是一个有序的序列,从第二个记录开始进行插入
 * 直接插入排序为稳定的。
 */
void InsertSort(int *a, int n);

/*
 * 插入排序-希尔排序(缩小增量排序)
 * 先将待排序序列分割成若干子序列分别进行直接插入排序
 * 待基本有序后在对全体进行直接插入排序
 * 希尔排序不稳定
 */
void ShellSort(int *a, int n);

void SSort(int *a, int n, int dk);

/*
 * 选择排序-简单选择排序
 * 在待排记录中,第一趟选择选择最小的数与第一个位置交换,第一个元素即为有序序列
 * 第二趟在无序序列中选择最小的数与第二个位置交换,此时前两个元素为有序序列
 * 共选择n-1次就可得到完整的有序序列
 * 改进:二路选择排序
 */
void SimpleSelectSort(int *a, int n);

/*
 * 交换排序--冒泡排序
 * 每一趟相邻元素比较,将最小的排到首位置
 * 改进:1.在序列已经有续时终止排序
 *       2.两路冒泡,一趟循环将最大最小的数据放在两端,循环次数减少一半
 */
void BubbleSort(int *a, int n);

/*
 * 交换排序--快速排序
 * 选择一个基本元素,通常选第一个或者最后一个元素
 * 通过一趟排序将待排序列分割为两部分,一部分比基准元素小,另一部分比基准元素大
 * 此时基准元素在其正确位置
 * 然后分别对这两部分用同样的方法继续排序
 */
int partition(int *a, int low, int high);
void QuickSort(int *a, int low, int high);


int main() {
    cout << "请输入元素个数:" << endl;
    cin >> n;
    cout << "请输入" << n << "个元素:" << endl;
    int *p;
    p = (int *) malloc(n * sizeof(int));
    for (int i = 0; i < n; i++) {
        cin >> p[i];
    }
    //InsertSort(p,n);
    //ShellSort(p,n);
    //SimpleSelectSort(p,n);
    //BubbleSort(p, n);
    //QuickSort(p,0,n-1);
    return 0;
}

void InsertSort(int *a, int n) {
    for (int i = 1; i < n; i++) {
        if (a[i] < a[i - 1]) {
            int j = i - 1;
            int x = a[i];//x作为哨兵
            while (x < a[j] && j >= 0)//不写j>=0发生数组越界
            {
                a[j + 1] = a[j];
                j--;
            }
            a[j + 1] = x;
        }
        show(a, i,n);
    }

}

void ShellSort(int *a, int n) {
    int dk = n / 2;
    int i = 1;
    while (dk >= 1) {
        SSort(a, n, dk);
        show(a,i,  n);
        i++;
        dk /= 2;//注意增量的变化
    }
}

void SSort(int *a, int n, int dk) {
    for (int i = dk; i < n; i++) {
        if (a[i] < a[i - dk]) {
            int j = i - dk;
            int x = a[i];
            while (x < a[j] && j >= 0) {
                a[j + dk] = a[j];
                j -= dk;
            }
            a[j + dk] = x;
        }
    }
}


void SimpleSelectSort(int *a, int n) {
    int index = 0;
    for (int i = 0; i < n - 1; i++) {
        index = i;
        for (int j = i + 1; j < n; j++) {
            if (a[j] < a[index]) {
                index = j;
            }
        }
        if (i != index) {
            swap(a[i], a[index]);
        }
        show(a,i+1, n);
    }
}

void BubbleSort(int *a, int n) {
    for (int i = 0; i < n - 1; i++) {
        for (int j = 0; j < n - i - 1; j++) {
            if (a[j] > a[j + 1]) {
                swap(a[j], a[j + 1]);
            }
        }
        show(a, i+1, n);
    }
}

int partition(int *a, int low, int high) {
    int pivot = a[low];
    while (low < high) {
        while (low < high && a[high] >= pivot) high--;
        swap(a[low], a[high]);
        while (low < high && a[low] <= pivot) low++;
        swap(a[low],a[high]);
    }
    show(a,n);
    return low;
}

void QuickSort(int *a, int low, int high) {
    if(low<high){
        int pivot=partition(a,low,high);
        QuickSort(a,low,pivot-1);
        QuickSort(a,pivot+1,high);
    }
}

void show(int *p, int n) {
    for (int i = 0; i < n; i++) {
        cout << p[i] << " ";
    }
    cout << endl;
}
void show(int*p,int j,int n){
    cout<<"第"<<j<<"次排序结果为:";
    for (int i = 0; i < n; i++) {
        cout << p[i] << " ";
    }
    cout << endl;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

怡人蝶梦

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值