文章详情

  • 游戏榜单
  • 软件榜单
关闭导航
热搜榜
热门下载
热门标签
php爱好者> php文档>编程珠玑之排序

编程珠玑之排序

时间:2010-11-05  来源:小培

 

  isort3比isort2块15%。

  如果输入数组几乎是有序的,那么插入排序的速度会快很多,因为每个元素的移动距离很短。

2.快速排序
  快速排序对于大数据量的排序非常有效。
  第一个版本:
  void qsort1(l,u)
        ifl>= u           // l should little than u
               return;  
        m = l;            //use the first data to split, flagdata
        for i =[l+1,u]    //scan from the second data
               if( x[i] < x[l] ) // the data is little than thefirst data
                       swap(++m,i);  //m should little than i, swap the data
        swap(l,m); //m is the write data to set the flag data
        qsort1(1,m-1);
        qsort1(m+1,u);

  运用哨兵,进行代码优化
  void qsort2a(l,u)
        if l>=u           // l should little than u
               return;          
        t = x[l];         //use the first data to split, flag data
        m= u+1;
        for( i = u;i>=l;i--)
               if(x[i]>=t)    //even if x[i]== t, also swap
                       swap(--m,i);       
        qsort2a(1,m-1);
        qsort2a(m+1,u);
  对2a算法,利用哨兵进行二次优化:
  void qsort2aa(l,u)
        if l>=u           // l should little than u
               return;          
        t = x[l];         //use the first data to split, flag data
        m=i = u+1;
        do
           while x[--i] < t ;
           swap(--m,i);
        while i!=l

        qsort2aa(1,m-1);
        qsort2aa(m+1,u);
 
  哨兵位置变化的算法,哨兵变为x[u],
  void qsort2b(l,u)
        if l>=u           // l should little than u
               return;          
        t = x[u];         //use the first data to split, flag data
        m= l-1;
        fori = [l,u]
               if( x[i] <= t )
                       swap(++m,i);               
        qsort2b(1,m-1);
        qsort2b(m+1,u);
  对于qsort2b算法,利用哨兵进行的二次优化。
  void qsort2b(l,u)
        if l>=u           // l should little than u
               return;          
        t = x[u];         //use the first data to split, flag data
        m= i = l-1;
        do
           while x[++i] > t ;
           swap(++m,i);
        while i!=u;       
        qsort2b(1,m-1);
        qsort2b(m+1,u);
 

  对于拥有n个相同数据的数组,以上的算法,时间量级退化为为o(n*n).
  这个时候使用双向划分,数据相等的时候,停止。
  循环不变式为: t=x[l];l<=i<=j<=u;  l<a<b<u => x[a]<=x[b]
  下标i,j初始化为待划分数组的两端。主循环中有两个内循环,第一个内循环将i向右移过小元素,遇到大元素停止;第二个内循环将j向左移过大元素,遇到小元素停止。然后主循环测试这两个下标是否交叉并交换它们的值。
  但是当元素相同的时候,停止扫描,并交换i,j的值。
  实现代码:
  void qsort3(l,u)
        ifl>= u           // l should little than u
               return;          
        t = x[l]; //flag
        i = l; j= u+1;   //init the i,j
        loop
           do i++ while i<=u && x[i] < t
           do j++ while x[i] > t
            if i>j
               break
           swap(i,j);
        swap(l,j);
        qsort3(1,m-1);
        qsort3(m+1,u);
  针对qsort3的改善点:
   1.flag的值设置为第一个,当给的数据基本有序的时候,程序的性能会变差,所以可以用rand()函数定位,先将第一个数据和定位到的数据交换。提高性能。
   2.当l,u距离比较小的时候,快速排序的效率会降低,这个时候可以采用其他的排序方法进行排序,以提高整体的排序效率。
   3.将swap函数进行适当的展开。
  经过优化的函数为:
  void qsort4(l,u,coff)  //coff 停止扫描的u-l差距。一般设置为50.
        ifu-l<coff       // 停止扫描的阀值检测
               return;  
        swap(l,randint(l,u));       
        t = x[l]; //flag
        i = l; j= u+1;   //init the i,j
        loop
           do i++ while i<=u && x[i] < t
           do j++ while x[i] > t
            if i>j
               break
           temp=x[i]; x[i]=x[j]; x[j]=temp;   //展开swap
        swap(l,j);
        qsort4(1,m-1);
        qsort4(m+1,u);        

相关阅读 更多 +
排行榜 更多 +
西安交大通

西安交大通

生活实用 下载
长江云通

长江云通

生活实用 下载
translatez

translatez

生活实用 下载