zoukankan      html  css  js  c++  java
  • 数据结构几类排序的总结和完整代码 待续。。

    一 插入排序

    • 简单插入排序
    • 希尔排序

    二 快速排序

          快排是冒泡排序的改进,每做一次排序可以确定一个数最终的位置p,同时把所有小于这个数的放在它左边,小于这个数的放在它后面。再递归地进行p左边部分和p右边部分的排序就可以了。  

     代码:   

     1 #include<iostream>
     2 #include<cstdio>
     3 using namespace std;
     4 
     5 int a[100002],count1=0,n;
     6 
     7 int each_sort(int low,int high)
     8 {
     9     int temp=a[low];
    10     while(low<high)
    11     {
    12         while(low<high&&a[high]>=temp)//找到high指向的<temp的值 一到前面来
    13             high--;
    14         a[low]=a[high];
    15         while(low<high&&a[low]<=temp)// 找到low指向的temp的值 移到后面去
    16             low++;
    17         a[high]=a[low];
    18     }
    19     a[low]=temp;
    20     return low;
    21 }
    22 
    23 
    24 void Qsort(int low,int high)
    25 {
    26     int position;
    27     if(low<high)
    28     {
    29         position=each_sort(low,high);
    30         Qsort(low,position-1);
    31         Qsort(position+1,high);
    32     }
    33 }
    34 
    35 void in()
    36 {
    37     printf("输入要排序列的个数:n
    ");
    38     scanf("%d",&n);
    39     printf("依次输入要排的n个数
    ");
    40     for(int i=0; i<n; i++)
    41         scanf("%d",&a[i]);
    42 }
    43 
    44 void out()
    45 {
    46     printf("
    结果:
    ");
    47     for(int i=0; i<n; i++)
    48         printf("%d ",a[i]);
    49     printf("
    ");
    50 }
    51 
    52 int main()
    53 {
    54     while(1)
    55     {
    56         in();
    57         Qsort(0,n-1);
    58         out();
    59     }
    60     return 0;
    61 }
    View Code

    三 选择排序

            每次在i...n这段中选一个最小的记录放在i位置(n为序列总长度,i为1遍历到n的值)。

    • 简单选择排序
       1 #include<iostream>
       2 #include<cstdio>
       3 #define maxx 9999999
       4 using namespace std;
       5 
       6 int a[100002],count1=0;
       7 int n;
       8 
       9 void Qsort()
      10 {
      11     for(int i=1; i<=n; i++)
      12     {
      13         int minn=i;
      14         for(int j=i+1; j<=n; j++)
      15             if(a[minn]>a[j])
      16                 minn=j;
      17         swap(a[i],a[minn]);
      18     }
      19 }
      20 
      21 void in()
      22 {
      23     printf("输入要排序列的个数:n
      ");
      24     scanf("%d",&n);
      25     printf("依次输入要排的n个数
      ");
      26     for(int i=1; i<=n; i++)
      27         scanf("%d",&a[i]);
      28 }
      29 
      30 void out()
      31 {
      32     for(int i=1; i<=n; i++)
      33         printf("%d ",a[i]);
      34     printf("
      ");
      35 
      36 }
      37 
      38 int main()
      39 {
      40     while(1)
      41     {
      42         in();
      43         Qsort();
      44         out();
      45     }
      46     return 0;
      47 }
      View Code
    • 树形选择排序(锦标赛排序)  :简单选择排序每一趟平均的比较次数是n/2,其中很多次都是重复的导致效率较低,树形选择排序则改善了这个问题,每一趟的平均比较次数是logn。讲要排序的n个数两两比较,其中(n+1)/2个较小者再两两比较,如此重复知道选出了最小的关键字为止,选择次小,只要把最小的关键字的叶子节点的值改成无限大,再和其左(右)兄弟进行比较,修改从叶子节点到根节点的路径上的值)   
    • 堆排     树形选择排序缺点有辅助空间较多,最大值进行多次比较。二堆排序只需要一个记录大小的辅助空间。每个待排记录只需一个存储空间。 
       

     

     1 #include<iostream>
     2 #include<cstdio>
     3 #define maxx 9999999
     4 using namespace std;
     5 
     6 int a[100002],count1=0;
     7 int n;
     8 
     9 void adjust(int s,int n)
    10 {
    11     int i,temp=a[s],temps=s;
    12     for( i=s*2; i<=n; i=i*2)
    13     {
    14         if(i<n&&a[i]>a[i+1])
    15             i++;
    16         if(i<=n&&a[i]>a[s])
    17             break;            // (若求的是大顶堆)当a[s]值比s的左右兄弟都大, 则不需要向下调整了  
    18         a[s]=a[i];    // s和s的左右兄弟里最大的是第i个(i!=s)
    19         s=i;
    20     }
    21     a[s]=temp ;
    22 }
    23 
    24 void Qsort()
    25 {
    26     for(int i=n/2; i>0; i--)
    27         adjust(i,n);    //从最后一个非叶子结点开始,将他调整为大顶堆
    28     for(int i=n; i>1; i--)
    29     {
    30         swap(a[1],a[i]);    //a[1]为以选出的最大值    和a[i]交换
    31         adjust(1,i-1);     //对前i-1筛选,调整为大顶堆
    32     }
    33     printf("
    ");
    34 }
    35 
    36 void in()
    37 {
    38     printf("输入要排序列的个数:n
    ");
    39     scanf("%d",&n);
    40     printf("依次输入要排的n个数
    ");
    41     for(int i=1; i<=n; i++)
    42         scanf("%d",&a[i]);
    43 }
    44 
    45 void out()
    46 {
    47     for(int i=n; i>=1; i--)
    48         printf("%d ",a[i]);
    49     printf("
    ");
    50 
    51 }
    52 
    53 int main()
    54 {
    55     while(1)
    56     {
    57         in();
    58         Qsort();
    59         out();
    60     }
    61     return 0;
    62 }
    View Code

    四 归并排

    2-路归并排序时典型的分治算法,归并的含义是:将两个有序序列合成一个有序序列。用递归的写法可以很直观的表达

     1 #include<iostream>
     2 #include<cstdio>
     3 using namespace std;
     4 
     5 int a[100002],count1=0,n;
     6 int b[100002];
     7 
     8 void Merge(int s,int t,int m)
     9 {
    10     int i,k,j;
    11     for(int i=s;i<=t;i++)
    12         b[i]=a[i];        //把s...t段的a  拷贝给b
    13     for(k=s,j=m+1,i=s;i<=m&&j<=t;k++)
    14     {
    15         if(b[i]<b[j]) a[k]=b[i++];
    16         else a[k]=b[j++];
    17     }
    18     while(i<=m)
    19         a[k++]=b[i++];// 剩下的b[i....m]复制到a中
    20     while(j<=t)
    21         a[k++]=b[j++];// 剩下的b[j....t]复制到a中
    22 
    23 }
    24 
    25 void Msort(int s,int t)
    26 {
    27     if(s<t)
    28     {
    29         int mid=(s+t)/2;
    30         Msort(s,mid);
    31         Msort(mid+1,t);
    32         Merge(s,t,mid);// 此时s..mid 和 mid+1..t段都是有序的了,再合并这两部分为一个有序的
    33     }
    34 }
    35 
    36 
    37 void in()
    38 {
    39     printf("输入要排序列的个数:n
    ");
    40     scanf("%d",&n);
    41     printf("依次输入要排的n个数
    ");
    42     for(int i=0; i<n; i++)
    43         scanf("%d",&a[i]);
    44 }
    45 
    46 void out()
    47 {
    48     printf("
    结果:
    ");
    49     for(int i=0; i<n; i++)
    50         printf("%d ",a[i]);
    51     printf("
    ");
    52 }
    53 
    54 int main()
    55 {
    56     while(1)
    57     {
    58         in();
    59         Msort(0,n-1);
    60         out();
    61     }
    62     return 0;
    63 }
    View Code

    五 基数排序

  • 相关阅读:
    BZOJ2219数论之神——BSGS+中国剩余定理+原根与指标+欧拉定理+exgcd
    Luogu 3690 Link Cut Tree
    CF1009F Dominant Indices
    CF600E Lomsat gelral
    bzoj 4303 数列
    CF1114F Please, another Queries on Array?
    CF1114B Yet Another Array Partitioning Task
    bzoj 1858 序列操作
    bzoj 4852 炸弹攻击
    bzoj 3564 信号增幅仪
  • 原文地址:https://www.cnblogs.com/assult/p/3974192.html
Copyright © 2011-2022 走看看