常用排序模板

19 篇文章 0 订阅
2 篇文章 0 订阅
  1. 快速排序
    其思想是:先选一个“标尺”,
    用它把整个队列过一遍筛子,
    以保证:其左边的元素都不大于它,其右边的元素都不小于它。
    这样,排序问题就被分割为两个子区间。
    再分别对子区间排序就可以了。

  2. 选择排序
    思想:重复选择数组内的最大值,交换到合适的位置。该排序方法比较慢。

  3. 堆排序
    思想:堆实际上是一棵完全二叉树,利用大顶堆(小顶堆)堆顶记录的是最大关键字(最小关键字)这一特性,使得每次从无序中选择最大记录(最小记录)。堆排序其实也是一种选择排序,是一种树形选择排序。

  4. 归并排序
    思想:这是一个采用分治法的算法,先使每个子序列有序,再使子序列段间有序,再将已有序的子序列合并,这样就能得到完全有序的序列。
  5. 桶排序
    构建一个哈希函数Hash(Ai)用以均匀的将n个元素分配到n个桶中。
    代码一起上
#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <conio.h>
#include <cmath>
#include <iostream>

#define MAXSIZE 120
#define FALSE 0
#define TRUE 1
using namespace std;
typedef struct
{
    int r[MAXSIZE + 1];
    int length;
} SqList;
typedef int  RedType;
int CompareCount;
//随意数据的生成
void SortInit(SqList *L)
{
    int i, j, temp;
    L->r[1] = (rand() % 1000);
    for (i = 2; i <= MAXSIZE; i++)
    {
        do
        {
            temp = (rand() % 1000);
            for (j = 1; j < i; j++)
                if (temp == L->r[j])
                    break;
        } while (j < i);
        L->r[i] = temp;
    }
    L->length = MAXSIZE;
}
//数据拷贝
void DataCopy(SqList L, SqList &L1)
{

    L1.length = L.length;
    for (int i = 1; i <= L.length; i++)
        L1.r[i] = L.r[i];
}

//直接插入排序
void InsertSort(SqList &L)
{
    int i, j;
    CompareCount = 0;
    for (i = 2; i <= L.length; i++)
    {
        CompareCount++;
        if (L.r[i] < L.r[i - 1])
        {
            L.r[0] = L.r[i];
            for (j = i - 1; L.r[0] < L.r[j]; j--)
            {
                L.r[j + 1] = L.r[j];
                CompareCount++;
            }
            L.r[j + 1] = L.r[0];
        }
    }
}
//希尔排序
void ShellInsert(SqList &L, int dk)
{
    int  j;
    for(int i = dk +1 ;i<=L.length;i++){
        CompareCount++;
        if(L.r[i]<L.r[i-dk]){
            L.r[0]=L.r[i];
            for( j = i-dk; j>0&&L.r[0]<L.r[j];j-=dk){
                L.r[j+dk] = L.r[j];
                CompareCount++;
            }
            L.r[j+dk] = L.r[0];
        }
    }
    return;
}

void ShellSort(SqList &L )
{
    CompareCount = 0;
    for(int d = L.length/2; d > 0; d/=2){
        ShellInsert(L,d);
    }
    return;
}

//冒泡排序
void BubbleSort(SqList &L)
{
    CompareCount = 0;
    int t, flag=1;
    int m = L.length-1;
    while(m>0&&flag==1){
        flag = 0;
        CompareCount++;
        for(int j=1;j<=m;j++){
            CompareCount++;
            if(L.r[j]>L.r[j+1]){
                flag =1;
                t= L.r[j];
                L.r[j]= L.r[j+1];
                L.r[j+1]=t;
            }
        }
        m--;
    }
}

//快排
int Partition(SqList &L, int low, int high)
{
    int pivot;
    L.r[0] = L.r[low];
    pivot = L.r[low];
    while(low<high){
        CompareCount++;
        while(low < high&&L.r[high]>=pivot){
            CompareCount++;
            high--;
        }
        L.r[low] = L.r[high];
        while(low < high&&L.r[low]<= pivot){
            CompareCount++;
            low++;
        }
        L.r[low]= L.r[0];
        return low;
    }
}

void QuickSort(SqList &L, int low, int high)
{
    int pivotloc;
    if (low <high){
        pivotloc = Partition(L,low,high);
        QuickSort(L,low,pivotloc-1);
        QuickSort(L,pivotloc+1,high);
    }
    return;
}
void QSort(SqList &L){
    CompareCount = 0;
    QuickSort(L,1,L.length);
}

//直接选择排序
void SelectSort(SqList &L) //直接选择排序
{
    CompareCount = 0;
    int temp;
    int i,j,k;
    for (i=1; i<L.length; ++i)//在L.r[i..L.length] 中选择key最小的记录
    {
        CompareCount++;
        k=i;
        for( j=i+1;j<=L.length ; j++){ //查找最小的元素
            CompareCount++;
            if ( L.r[j] <L.r[k]){
                k=j;
            }
        }
        if(k!=i)
        {
            temp=L.r[i];
            L.r[i]=L.r[k];
            L.r[k]=temp;
        }
    }
}

//堆排序
void HeapAdjust(SqList &L, int s, int m)// 算法10.10
{ // 已知H.r[s..m]中记录的关键字除H.r[s].key之外均满足堆的定义,本函数
  // 调整H.r[s]的关键字,使H.r[s..m]成为一个大顶堆(对其中记录的关键字而言)
    RedType rc;
    int j;
    rc=L.r[s];
    for(j=2*s;j<=m;j*=2)
    { // 沿key较大的孩子结点向下筛选
        CompareCount++;
        if(j<m&&L.r[j]<L.r[j+1]){
            ++j; // j为key较大的记录的下标
        }
        if(rc>L.r[j])
            break; // rc应插入在位置s上
        L.r[s]=L.r[j];
        s=j;
    }
    L.r[s]=rc; // 插入
}
void HeapSort(SqList &L)
{ // 对顺序表H进行堆排序。算法10.11
    RedType t;
    int i;
    CompareCount = 0;
    for(i=L.length/2;i>0;--i) {// 把H.r[1..H.length]建成大顶堆
        HeapAdjust(L,i,L.length);
        CompareCount++;
    }
    for(i=L.length;i>1;--i)
    { // 将堆顶记录和当前未经排序子序列H.r[1..i]中最后一个记录相互交换
        t=L.r[1];
        L.r[1]=L.r[i];
        L.r[i]=t;
        CompareCount++;
        HeapAdjust(L,1,i-1); // 将H.r[1..i-1]重新调整为大顶堆
    }
}


//归并排序
void Merge(RedType SR[],RedType TR[],int i,int m,int n)
{ // 将有序的SR[i..m]和SR[m+1..n]归并为有序的TR[i..n] 算法10.12
    int j,k,l;
    for(j=m+1,k=i;i<=m&&j<=n;++k) // 将SR中记录由小到大地并入TR
    {
        CompareCount++;
        if(SR[i] <= SR[j]){
            TR[k]=SR[i++];
        }

        else{
            TR[k]=SR[j++];
        }

    }
    if(i<=m)
        for(l=0;l<=m-i;l++){
                CompareCount++;
            TR[k+l]=SR[i+l]; // 将剩余的SR[i..m]复制到TR
        }

    if(j<=n)
        for(l=0;l<=n-j;l++){
                CompareCount++;
            TR[k+l]=SR[j+l]; // 将剩余的SR[j..n]复制到TR
        }

}

void MSort(RedType SR[],RedType TR1[],int s, int t)
{ // 将SR[s..t]归并排序为TR1[s..t]。算法10.13
    int m;
    RedType TR2[MAXSIZE+1];
    if(s==t)
        TR1[s]=SR[s];
    else
    {
        m=(s+t)/2; // 将SR[s..t]平分为SR[s..m]和SR[m+1..t]
        MSort(SR,TR2,s,m); // 递归地将SR[s..m]归并为有序的TR2[s..m]
        MSort(SR,TR2,m+1,t); // 递归地将SR[m+1..t]归并为有序的TR2[m+1..t]
        Merge(TR2,TR1,s,m,t); // 将TR2[s..m]和TR2[m+1..t]归并到TR1[s..t]
    }
}
void MergeSort(SqList &L)
{ // 对顺序表L作归并排序。算法10.14
    CompareCount = 0;
    MSort(L.r,L.r,1,L.length);
}
//输出排序结果
void OutputSortData(SqList L)
{
    int i;
    for (i = 1; i <= MAXSIZE; i++)
    {
        if ((i - 1) % 10 == 0)
            printf("\n");
        printf("%6d", L.r[i]);
    }

    getchar();
    cout <<endl;
}

//进行7种排序并输出结果
void sort(SqList L, SqList &L1, int a[20][2], int No)
{
    cout <<"初始化的数据为:"<<endl;
    OutputSortData(L);

    //直接插入排序
    cout <<"直接插入排序"<<endl;
    DataCopy(L, L1);
    InsertSort(L1);
    a[1][No] = CompareCount;
    OutputSortData(L1);

    //希尔排序
    cout <<"希尔排序"<<endl;
    DataCopy(L, L1);
    ShellSort(L1);
    a[2][No] = CompareCount;
    OutputSortData(L1);

    //冒泡排序
    cout <<"冒泡排序"<<endl;
    DataCopy(L, L1);
    BubbleSort(L1);
    a[3][No] = CompareCount;
    OutputSortData(L1);

    //快速排序
    cout <<"快速排序"<<endl;
    DataCopy(L, L1);
    CompareCount = 0;
    QSort(L1);
    a[4][No] = CompareCount;
    OutputSortData(L1);

    //直接选择排序
    cout <<"直接选择排序"<<endl;
    DataCopy(L, L1);
    SelectSort(L1);
    a[5][No] = CompareCount;
    OutputSortData(L1);

    //堆排序
    cout <<"堆排序"<<endl;
    DataCopy(L, L1);
    HeapSort(L1);
    a[6][No] = CompareCount;
    OutputSortData(L1);

    //归并排序
    cout <<"归并排序"<<endl;
    DataCopy(L, L1);
    MergeSort(L1);
    a[7][No] = CompareCount;
    OutputSortData(L1);
}

int  main()
{
    int i, a[20][2];
    char SortName[][15] = {"", "直接插入排序", "希尔排序", "冒泡排序", "快速排序", "直接选择排序", "堆排序","归并排序"};
    SqList L, L1, L2, L3;
    SortInit(&L);
    printf("(一)排序的结果为:\n");
    sort(L, L1, a, 0);
    printf("(二)各排序的比较次数为:\n");
    for (int i = 1; i <= 7; i++) {
        cout << SortName[i] << endl;
        printf("%d\n", a[i][0]);
        cout << endl;
    }
    system("pause");
    return 0;
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值