• 常用排序算法(转)


    1.插入排序

    由N-1趟排序组成,对于p=1到p=N-1趟,插入排序保证从位置0到位置p上的元素为已排序状态。

    时间复杂度:O(N^2)

    代码
    void InsertionSort(ElementType A[],int N)
    {
      
    int j,p;
      ElementType Tmp;
      
    for(p=1;p<N;p++)
      {
        Tmp
    =A[j];//把A[j]保存下来,因为它要被插入到前面的某个位置去
        for(j=p;j>0&&A[j-1]>Tmp;j--)//大于A[j]的元素逐个后移
         {
           A[j]
    =A[j-1];
         }
        A[j]
    =Tmp;
      }
    }

    2.希尔排序

    希尔排序使用一个序列h1,h2,h3,ht,叫做增量排序。在使用增量hk的一趟排序之后,对于每个i我们有A[i]<A[i+hk],所有相隔hk的元素被排序。

    时间复杂度:O(N^(1+a)),其中0<a<1。

    代码
    //代码不太好理解,使用了3层循环
    void ShellSort(ElementType A[],int N)
    {
        
    int j,p,Increment;
        ElementType Tmp;
        
    for(Increment=N/2;Increment>0;Increment/=2)
        {
            
    for(p=Increment;p<N;p++)
            {
                Tmp
    =A[p];
                
    for(j=p;j>=Increment;j-=Increment)
                {
                    
    if(A[j]<A[j-Increment])
                        A[j]
    =A[j-Increment];
                    
    else
                        
    break;
                }
                A[j]
    =Tmp;
            }
        }
    }

    3. 堆排序

    思想:建立小顶堆,然后执行N次deleteMin操作。

    时间复杂度:O(NlogN),实践中,慢于sedgewick的希尔排序

    空间复杂度:O(N),用于建立堆得数组

    4.归并排序

    使用递归把数组分为两部分分别排序,然后合并成一个数组

    时间复杂度:O(NlogN)

    空间复杂度:O(N)

    代码
    void Merge(ElementType A[],ElementType TmpArray[], int Lpos, int Rpos, int RightEnd)
    {
        
    int i, LeftEnd, NumELements,TmpPos;
        LeftEnd
    =Rpos-1;
        TmpPos
    =Lpos;
        NumElements
    =RightEnd-Lpos+1;
        
    while(Lpos<=LeftEnd&&Rpos<=RightEnd)
            TmpArray[TmpPos
    ++]=(A[Lpos]<A[Rpos])?A[Lpos++]:A[Rpos++];
        
    while(Lpos<LeftEnd)
            TmpArray[TmpPos
    ++]=A[Lpos++];
        
    while(Rpos<RightEnd)
            TmpArray[TmpPos
    ++]=A[Rpos++];

        
    for(i=0;i<NumElements;i++,RightEnd--)
            A[RightEnd]
    =TmpArray[RightEnd];
    }

     5.快速排序

    对于小数组(N<20),快排不如插排好。一种好的截止范围是N=10,大于10则用快排。

    快排的四步:

    ①如果S中元素个数是0或1,则返回

    ②取S中间元素v为枢纽元

    ③将S-{v}分成两个不相交的集合:分别是S1(小于v),和大于v的部分S2

    ④返回quicksort(S1),继随v,继而quicksort(S2)

    时间复杂度:O(NlogN)

    编程思想:1.选取枢纽元,取首尾及中间的三个元素,排序,小的排在首位,大的排在尾部,中的作为枢纽元

    2.排序时把枢纽元放在Right-1的位置上,i=Left+1;j=Right-2;开始交换过程

    代码
    ElementType Median3(ElementType A[],int Left, int Right)
    {
        
    int center =(Left+Right)/2;
        
    if(A[Left]>A[Center])
            swap(
    &A[Left],&A[Center]);
        
    if(A[Left]>A[Right])
            swap(
    &A[Left],&A[Right]);
        
    if(A[Center]>A[Right])
            swap(
    &A[Center],&A[Right]);

        swap(
    &A[Center],&A[Right-1]);
        
    return A[Right-1];
    }

    Qsort(ElementType A[],
    int Left,int Right)
    {
        
    int i,j;
        ElementType Pivot;
        
    if(Left+9<Right)    //10个元素以上的数组使用快排
        {
            Pivot
    =Median3(A[],Left,Right);
            i
    =Left+1;
            j
    =Right-2;
            while(1)
            {
            
    while(A[i++]<Pivot);
            
    while(A[j--]>Pivot);
            
    if(i<j)
                swap(
    &A[i],&A[j])
            
    else
                
    break;
            }
            swap(
    &A[i],&A[Right-1]);
            Qsort(A,Left,i
    -1);
            Qsort(A,i
    +1,Right);
        }
        
    else
            InsertSort(A,Right
    -Left+1);
    }

     6.直接选择排序

    描述:选出数组中最小的元素,与数组的第一个元素交换;然后选择出数组中次小的元素,与与第二个元素交换,直到完成

    选择排序需要比较N(N-1)/2次,即N2次,而交换则只需要N-1

    对于是否已经排好序,或者随机文件,所花费的时间是一致的,即执行时间具有强迫性

    选择排序应用在数据项比较大,键比较小的情况下,因为此时移动元素花费时间较多,而对于其他排序算法,元素移动频繁的多

    代码
    void sort(ElementType A[], int N) 

      
    int i, j; 
      
    int min; 
      
    for(i=0; i<N-1; i++
      { 
        min 
    = i; 
        
    for(j=i+1; j<=N-1; j++
        
    if(A[j]<A[min]) min=j; 
          swap(A[i],A[min]); 
      }    

  • 相关阅读:
    dubbo源码阅读-服务调用之远程调用(十二)
    dubbo源码阅读-注册中心(十三)之Zookeeper
    dubbo源码阅读-远程暴露(七)之Transport
    dubbo源码阅读-远程暴露(七)之Exchangers
    dubbo源码阅读-服务调用(十二)之本地调用(Injvm)
    dubbo源码阅读-ProxyFactory(十一)之StubProxyFactoryWrapper本地存根
    dubbo源码阅读-服务暴露(七)之本地暴露(Injvm)
    dubbo源码阅读-ProxyFactory(十一)之JavassistFactory
    OpenCV 实现颜色直方图
    FFMPEG结构体分析:AVPacket
  • 原文地址:https://www.cnblogs.com/buffer/p/1619258.html
Copyright © 2020-2023  润新知