Chinaunix首页 | 论坛 | 博客
  • 博客访问: 119588
  • 博文数量: 32
  • 博客积分: 506
  • 博客等级: 下士
  • 技术积分: 257
  • 用 户 组: 普通用户
  • 注册时间: 2012-07-11 11:06
文章分类

全部博文(32)

文章存档

2012年(32)

分类: C/C++

2012-10-26 09:32:29

交换排序的基本思想是:两两比较待排序记录的关键字,发现两个记录的次序相反时即进行交换,直到没有反序的记录为止。
     应用交换排序基本思想的主要排序方法有:冒泡排序和快速排序。
1,冒泡排序:冒泡算法的平均时间复杂度为O(n2)
   排序方法:
    将被排序的记录数组R[1..n]垂直排列,每个记录R[i]看作是重量为R[i].key的气泡。根据轻气泡不能在重气泡之下的原则,从下往上扫描数组R:凡扫描到违反本原则的轻气泡,就使其向上"飘浮"。如此反复进行,直到最后任何两个气泡都是轻者在上,重者在下为止。
 
算法实例:R(l..n)是待排序的文件,采用自下向上扫描,对R做冒泡排序

点击(此处)折叠或打开

  1. void BubbleSort(SeqList R)
  2. {
  3.     int i,j,KEY;
  4.     BOOL exchange; //交换标志
  5.     
  6.     for(i =1,i
  7.     {
  8.         exchange = FALSE;//每趟排序开始前标志置为false
  9.         for(j= n-1;j>=i;j--)
  10.         {
  11.             if(R[j+1].key > R[j].key)
  12.             {
  13.                 KEY = R[j+1];
  14.                 R[j+1] = R[j];
  15.                 R[j] = KEY;
  16.                 exchange = TRUE; 
  17.             }
  18.         }
  19.         if(!exchange) //本次没有发生交换,整个排序已ok,提前结束排序
  20.         {
  21.             return;
  22.         }
  23.     }
  24. }
2,快速排序算法:
它采用了一种分治的策略,通常称其为分治法(Divide-and-ConquerMethod):分治法的基本思想是:将原问题分解为若干个规模更小但结构与原问题相似的子问题。递归地解这些子问题,然后将这些子问题的解组合为原问题的解。
在R[low..high]中任选一个记录作为基准(Pivot),以此基准将当前无序区划分为左、右两个较小的子区间R[low..pivotpos-1)和R[pivotpos+1..high],并使左边子区间中所有记录的关键字均小于等于基准记录(不妨记为pivot)的关键字pivot.key,右边的子区间中所有记录的关键字均大于等于pivot.key,而基准记录pivot则位于正确的位置(pivotpos)上,它无须参加后续的排序。
 
算法实现:

点击(此处)折叠或打开

  1. //划分算法:调用Partition(R,low,high)时,对R[low..high]做划分,并返回基准记录的位置
  2. int Partition(SeqList R,int i,int j)
  3. {
  4.     RecType pivot = R[i];//用区间第一个的记录作为基准
  5.    
  6.     while(i
  7.     {
  8.         while(i= pivot.key)
  9.         {
  10.            j--;//从右向左扫描,查找第1个关键字小于pivot.key的记录R[j]
  11.         }
  12.         if(i < j)
  13.         {
  14.             R[i++] = R[j];//将R[j]的值放在R[i]的位置上,然后i指针加1,此时j指针在R[j]不动,
  15.                           //   等待下面i指针找到的比pivot大的值放进来,
  16.         }
  17.       
  18.         while(i
  19.         {
  20.             i++;// /从左向右扫描,查找第1个关键字大于pivot.key的记录R[i]
  21.         }
  22.         if(i
  23.         {
  24.             R[j--] = R[i];//同理上面
  25.         }       
  26.     }
  27.     R[i] = pivot.key;//基准记录已被最后定位
  28.     return i;
  29. }
  30. //快速排序算法QuickSort:对R[low..high]快速排序
  31. void QuickSort(SeqList R,int low,int high)
  32. {
  33.     int pivotposition;
  34.     if(low < high)
  35.     {
  36.         pivotpostion = Partion(R,low,high);
  37.         QuickSort(R,low,pivotpostion - 1);//对左区间递归排序
  38.         QuickSort(R,pivotpostion + 1,high);//对右区间递归排序
  39.     } 
  40. }
尽管快速排序的最坏时间为O(n2),但就平均性能而言,它是基于关键字比较的内部排序算法中速度最快者,快速排序亦因此而得名。它的平均时间复杂度为O(nlgn)。快速排序是非稳定的,例如[2,2,1]。

 
阅读(5598) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~