基础排序算法代码(选择、冒泡、插入、归并、快排、堆排序)

考试复习中、考完看能不能整个图出来

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

// 新数组
int *NewArray(int size)
{
    return (int*)malloc(sizeof(int)*size);
}

//释放内存
void FreeArray(int a[])
{
    free(a);
}

// 求最小值
int mymin(int a, int b)
{
    int ret;
    if (a < b) ret = a;
    else ret = b;
    return ret;
}

// 交换函数
void Swap(int a[], int i, int j)
{
    int temp;
    temp = a[i];
    a[i] = a[j];
    a[j] = temp;
}

// 选择排序 平均复杂度O(n^2),最坏O(n^2),辅助空间O(1),不稳定
void SelectSort(int a[], int n)
{
    int i, j, temp, index;
    for (i=0; i<n-1; i++)
    {
        index = i;
        for (j=i+1; j<n; j++)
        {
            if (a[j] < a[index])
                index = j;
        }
        Swap(a, i, index);
    }
}

// 冒泡排序 平均复杂度O(n^2),最坏O(n^2),辅助空间O(1),稳定
void BubbleSort(int a[], int n)
{
    int i, j, temp;
    for (i=0; i<n-1; i++)
    {
        for (j=0; j<n-i-1; j++)
        {
            if (a[j] > a[j+1])
            {
                Swap(a, j, j+1);
            }
        }
    }
}

// 插入排序,最好O(n),最坏O(n^2),倒序时
void StraightSort(int a[], int n)
{
    int tmp;
    int i, j;
    for (i=1; i<n; i++)
    {
        tmp = a[i];
        for (j=i-1; j>=0&&tmp<a[j]; j--)
        {
            a[j+1] = a[j];
        }
        a[j+1] = tmp;
    }
}

// 归并
void Merge(int array[], int arr1[], int n1, int arr2[], int n2)
{
    int p, p1, p2;
    p = p1 = p2 = 0;
    while (p1 < n1 && p2 < n2){
        if(arr1[p1] < arr2[p2]) array[p++] = arr1[p1++];
        else array[p++] = arr2[p2++];
    }
    while (p1 < n1) array[p++] = arr1[p1++];
    while (p2 < n2) array[p++] = arr2[p2++];
}

// 归并排序法(自顶向下)  平均复杂度O(nlogn),最坏O(nlogn),辅助空间O(n),稳定
void MergeSort1(int array[], int n)
{
    int i, n1, n2;
    int *arr1, *arr2;
    if (n<2) return;
    n1 = n / 2;
    n2 = n - n1;
    arr1 = NewArray(n1);
    arr2 = NewArray(n2);
    for (i=0; i<n1; i++)    
        arr1[i] = array[i];
    for (i=0; i<n2; i++)
        arr2[i] = array[n1+i];
    MergeSort1(arr1, n1);
    MergeSort1(arr2, n2);
    Merge(array, arr1, n1, arr2, n2);
    FreeArray(arr1);
    FreeArray(arr2);
}

// 归并排序法(自底向上)
void MergeSort2(int a[], int n)
{
    int s, *pa = a, *pb = NewArray(n);
    for (s = 1; s < n; s = s*2 ) {
        int k, *ptemp = pb;
        for (k = 0; k < n; k += s+s){
            Merge(pb + k, pa + k, s, pa + k + s, mymin(s, n - k - s));
            // 调试用的
            // for (int i=0; i<7; i++)
            // {
            //     printf("%d ", *(pb+i));
            // }
            // printf("\n");
        }
        // 为了不让pa和pb指向同一块内存地址
        pb = pa;
        pa = ptemp;
     }
    if (a!=pa)
        for (s = 0; s < n; s++) a[s] = pa[s];
}

// 快排(从左往右走)
void Qsort1(int a[], int low, int high)
{
    int pivot = a[low], s = low, t = s;
    int temp;
    if (low >= high) return;
    while (t <= high){
        if (a[t] <= pivot){
            Swap(a, s, t);
            s++;
        }
        t++;
    }
    s--;
    a[low] = a[s];
    a[s] = pivot;
    Qsort1(a, low, s-1);
    Qsort1(a, s+1, high);
}

// 快排(左右往中间走) O(nlogn),最差情况O(n^2),倒序时
void Qsort2(int a[], int low, int high)
{
     int s = low, t = high, pivot = a[ s ];
     if (low >= high) return;
     while ( s < t ) {
          while (t > s && a[ t ] >= pivot )  -- t;
          a[ s ] = a[ t ];  /* 将比key小的移到前面 */
          while ( s < t && a[ s ] <= pivot) ++ s;
          a[ t ] = a[ s ]; /*将比key大的移到后面*/
      }
     a[ s ] = pivot; /* 将key 保存回到数组 */
     Qsort2(a, low, s - 1); /* 递归 */
     Qsort2(a, s + 1, high); /* 递归 */
}

// 堆排序
// 最大堆调整
void MaxHeapify(int a[], int i, int n)
{
    /*
        最大堆调整,算法复杂度:O(堆的高度) = O(logn)
        i是待调整节点
        L是结点i的左孩子,R是结点i的右孩子
    */
    int L, R, max;
    L = 2*i+1;
    R = 2*(i+1);
    max = i;
    if (L < n && a[L] > a[max]) max = L;
    if (R < n && a[R] > a[max]) max = R;
    if (max!=i){
        Swap(a, i, max);
        MaxHeapify(a, max, n); // 递归调整
        
        // 调试用
        // for (int i=0; i<7; i++){
        //     printf("%d ", a[i]);
        // }
        // printf("\n");
    }
}

// 创建最大堆,算法复杂度O(n)
void BuildMaxHeap(int a[], int n)
{
    int i;
    for (i=n/2-1; i>=0; i--)  // n/2 ~ (n-1)都是叶子节点,0 ~ (n/2-1)为有孩子的节点
        MaxHeapify(a, i, n);
}

// 堆排序,算法复杂度O(nlogn)
void HeapSort(int a[], int n)
{
    BuildMaxHeap(a, n);
    while(n>=2)
    {
        Swap(a, 0, --n);  // 将最大值交换到末尾
        MaxHeapify(a, 0, n); // 最大化
    }
}

int main()
{
    int array[] = {49, 38, 65, 97, 76, 13, 27};
    // SelectSort(array, 7);
    // BubbleSort(array, 7);
    // StraightSort(array, 7);
    // MergeSort1(array, 7);
    // MergeSort2(array, 7);
    // Qsort1(array, 0, 6);
    // Qsort2(array, 0, 6);
    HeapSort(array, 7);
    
    //打印排序后的数组
    for (int i=0; i<7; i++){
        printf("%d ", array[i]);
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值