好得很程序员自学网

<tfoot draggable='sEl'></tfoot>

排序算法

排序算法

排序算法

算法导论中对排序问题的描述

输入 :n个数的序列<a 1 ,a 2 ,...,a n >。

输出 :输入序列的一个重排<a' 1 ,a' 2 ,...a' n >,使a' 1 <=a' 2 <=...<=a' n。

(首先声明下,下面的代码中伪代码是算法导论上抄的,c代码是自己写的。所以c语言的代码如果有问题请指教。)

1.插入排序

伪代码:

 1  INSERSION- SORT(A)
  2   for  j <-  2   to   length[A]
  3       do  key <-  A[j]
  4         i <- j- 1 
 5       while  i> 0   and  A[i]> key
  6           do  A[i+ 1 ] <-  A[i]
  7             i <- i- 1 
 8      A[i+ 1 ] <- key

c实现

  1   void  InsertionSort( int  A[], int   n)
   2   {
   3       int   key;
   4       int   i,j;
   5       for (i= 1 ;i<n;i++ )
   6       {
   7          key =  A[i];
   8          j = i- 1  ;
   9           while (key >= A[j] && j>= 0  )
  10           {
  11              A[j+ 1 ] =  A[j];
  12              j-- ;
  13           }
  14          A[j+ 1 ] =  key;
  15       }
  16  }

2.冒泡排序

伪代码:

 BUBBLESORT(A)
  for  i <-  1   to   length[A]
      do   for  j <- length[A]  downto  i+ 1 
            do   if  A[j]<A[j- 1  ]
                then  exchange A[j] <-> A[j- 1 ]

c实现:

  1   void  BubbleSort( int  A[], int   n)
   2   {
   3       int   i,j;
   4       int   tmp;
   5       for (i= 0 ;i<n;i++ )
   6       {
   7           for (j = n- 1 ;j>=i+ 1 ;j-- )
   8           {
   9               if (A[j]>A[j- 1  ])
  10               {
  11                  tmp =  A[j];
  12                  A[j] = A[j- 1  ];
  13                  A[j- 1 ] =  tmp;
  14               }
  15           }
  16       }
  17  }

在冒泡排序中如果做一个判断,在一趟起泡的过程中如果没有任何一次交换就终止循环。这样可以节省一些时间的开销。

3.归并排序

  1   MERGE(A,p,q,r)
   2  n1 <- q-p+ 1 
  3  n2 <- r- q
   4  creat arrays L[ 1 ...n1+ 1 ]andR[ 1 ...n2+ 1  ]
   5   for  i <-  1   to   n1
   6       do  L[i] <- A[p+i- 1  ]
   7   for  j <-  1   to   n2
   8       do  R[j] <- A[p+ j]
   9  L[n1+ 1 ] <-  ∞
  10  R[n2+ 1 ] <-  ∞
  11  i <-  1 
 12  j <-  1 
 13   for  k <- p  to   r
  14       do   if  L[i]<= R[j]
  15             then  A[k] <-  L[i]
  16                 i <- i+ 1 
 17             else  A[k] <-  R[j]
  18                 j <- j+ 1 
 19                 
 20  MERGE- SORT(A,p,r)
  21   if  p< r
  22      then  q <- └(p+q)/ 2  ┘
  23          MERGE- SORT(A,p,q)
  24          MERGE-SORT(A,q+ 1  ,r)
  25          MERGE(A,p,q,r)

c实现:

  1   void  Merge( int  A[], int  p, int  q, int   r)
   2   {
   3       int   n1,n2;
   4      n1 = q-p+ 1  ;
   5      n2 = r- q;
   6       int  *L = ( int  *)malloc( sizeof ( int )*(n1+ 1  ));
   7       int  *R = ( int  *)malloc( sizeof ( int )*(n2+ 1  ));
   8       int   i,j;
   9       for (i= 0 ;i<n1;i++ )
  10       {
  11          L[i] = A[p+ i];
  12       }
  13       for (j= 0 ;j<n2;j++ )
  14       {
  15          R[j] = A[q+j+ 1  ];
  16       }
  17      L[n1] =  INT_MAX;
  18      R[n2] =  INT_MAX;
  19      i =  0  ;
  20      j =  0  ;
  21       int   k;
  22       for (k=p;k<=r;k++ )
  23       {
  24           if (L[i]<= R[j])
  25           {
  26              A[k] =  L[i];
  27              i++ ;
  28           }
  29           else 
 30           {
  31              A[k] =  R[j];
  32              j++ ;
  33           }
  34       }
  35       free(L);
  36       free(R);
  37   }
  38   void  MergeSort( int  A[], int  p, int   r)
  39   {
  40       int   q;
  41       if (p< r)
  42       {
  43          q = p + (r-p)/ 2  ;
  44           MergeSort(A,p,q);
  45          MergeSort(A,q+ 1  ,r);
  46           Merge(A,p,q,r);
  47       }
  48  }

4.堆排序

伪代码:

  1   PARENT(i)
   2    return i* 2 
  3   LEFT(i)
   4     return 2i
   5   RIGHT(i)
   6    return  2 *i+ 1 
  7  MAX- HEAPIFY(A,i)
   8  l <-  LEFT(i)
   9  r <-  RIGHT(i)
  10   if  l<=heap-size[A]  and  A[l]> A[i]
  11      then  largest <-  l;
  12      else  largest <-  i;
  13   if  r<=heap-size(A)  and  A[r]> A[largest]
  14      then  largest <-  r
  15   if  largest !=  i
  16      then  exchange A[i] <->  A[largest]
  17          MAX- HEAPIFY(A,largest)
  18  BUILD-MAX- HEAP(A)
  19  heap-size[A] =  length[A]
  20   for  i <- └length[A]/ 2 ┘  downto   1 
 21       do  MAX- HEAPIFY(A,i)
  22  HEAP- SORT(A)
  23  BUILD-MAX- HEAP(A)
  24   for  i <-length[A]  downto   2 
 25       do  exchange A[ 1 ] <->  A[i]
  26         heap-size[A] <- heap-size[A]- 1 
 27         MAX-HEAPIFY(A, 1 )

c实现:

  1   #define  PARENT(i)(((i)-1)/2)
  2   #define  LEFT(i)(2*((i)+1)-1)
  3   #define  RIGHT(i)(2*((i)+1))
  4   void  MaxHeapify( int  A[], int  i, int   size)
   5   {
   6       int  l =  LEFT(i);
   7       int  r =  RIGHT(i);
   8       int  largest =  i;
   9       int   tmp;
  10       if (l<size && A[i]< A[l])
  11       {
  12          largest =  l;
  13       }
  14       if (r<size && A[r]> A[largest])
  15       {
  16          largest =  r;
  17       }
  18       if (largest !=  i)
  19       {
  20          tmp =  A[i];
  21          A[i] =  A[largest];
  22          A[largest] =  tmp;
  23           MaxHeapify(A,largest,size);
  24       }
  25   }
  26   void  BuildMaxHeap( int  A[], int   size)
  27   {
  28       int   i;
  29       for (i=size/ 2 ;i>= 0 ;i-- )
  30       {
  31           MaxHeapify(A,i,size);
  32       }
  33   }
  34   void  HeapSort( int  A[], int   size)
  35   {
  36       BuildMaxHeap(A,size);
  37       int   i;
  38       int   j;
  39       int   tmp;
  40       for (i=size- 1 ;i> 0 ;i-- )
  41       {
  42          tmp =  A[i];
  43          A[i] = A[ 0  ];
  44          A[ 0 ] =  tmp;
  45          MaxHeapify(A, 0  ,i);
  46       }
  47  }

5.基数加桶排序 (用了两个桶,分别装0,1)

基数排序伪代码:

 1  RADIX- SORT(A,D)
  2   for  i <-  1   to   d
  3       do  use a stable sort  to  sort  array  A on digit i

桶排序伪代码:

 1  BUCKET- SORT(A)
  2  n <-  length[A]
  3   for  i <-  1   to   n
  4       do   insert A[i] into list B[└nA[i]┘]
  5   for  i <-  0   to  n- 1 
 6       do  sort list B[i]  with   insertion sort
  7  concatenate the lists B[ 0 ],B[ 1 ],...,B[n- 1 ] together  in  order

c实现

  1   #define  GET(X,N)(((X>>(N-1))&0x1))/*获取第n bit*/
  2   void  RadixBucketSort( int  A[], int   n)
   3   {
   4       int  * Bucket = malloc( sizeof ( int )*n); /*  一个数组当两个桶用的  */ 
  5       int   i,j,z,num,pos1,pos2;
   6       for (num= 1 ;num< 32 ;num++ )
   7       {
   8          i = 0  ;
   9          j=n- 1  ;
  10           for (z= 0 ;z<n;z++ )
  11           {
  12               if (GET(A[z],num)== 1  )
  13               {
  14                  Bucket[i]= A[z];
  15                  i++ ;
  16               }
  17               else 
 18               {
  19                  Bucket[j]= A[z];
  20                  j-- ;
  21               }
  22           }
  23          pos1 =  0  ;
  24          pos2 = n- 1  ;
  25           for (z= 0 ;z<n;z++ )
  26           {
  27               if ( pos1!= i )
  28               {
  29                  A[z]= Bucket[pos1];
  30                  pos1++ ;
  31               }
  32               else 
 33               {
  34                  A[z]= Bucket[pos2];
  35                  pos2-- ;
  36               }
  37           }
  38  
 39       }
  40       free(Bucket);
  41  }

上面的算法中,算是基数排序加桶排序吧。我把一个数字从低到高每一个二进制位作为基数排序中的每一趟。也就是说我把一个int类型分成31个位。而每个二进制位只有1或0两种可能。所以将数据放入两个桶中时就自然的排好了序。所以我认为自己用了桶排序,呵呵。因为以上的原因,所以算法中只能对正数进行处理。如果要对负数或其他类型的数据进行排序的话,就要重新改进算法了。所以这些算法是有适用范围的。但比起比较排序,这些排序算法确实要快些。在数量很大的时候经过测试确实上面的算法比快排要快,呵呵。

 

 

分类:  algorithm

作者: Leo_wl

    

出处: http://www.cnblogs.com/Leo_wl/

    

本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。

版权信息

查看更多关于排序算法的详细内容...

  阅读:38次

上一篇: LUCENE.NET使用探秘

下一篇:python学习