数据结构(24)--排序篇之交换排序
2016-03-08 18:20
302 查看
参考书籍:数据结构(C语言版)严蔚敏吴伟民编著清华大学出版社
具体做法:
第一趟:第1个与第2个比较,大则交换;第2个与第3 比较,大则交换,… 关键字最大的记录交换到最后一个位置上;
第二趟:对前n-1个记录进行同样的操作,关键字次大 的记录交换到第n-1个位置上;依次类推,则完成排序。
![](https://oscdn.geek-share.com/Uploads/Images/Content/202009/03/14a627c24f06bd6b4c1d3d990c68fc63)
![](https://oscdn.geek-share.com/Uploads/Images/Content/202009/03/c4ff20ccec99087f7ea2ff874099c4ee)
逆序:需要进行n-1趟排序,需要进行n(n-1)/2次比较,并作等数量级的记录移动。总的时间复杂度为O(n^2) 。
起泡排序方法是稳定的。适合于数据较少的情况。
基本思想:通过一趟排序将待排序列以枢轴为标准划分成两部分,使其中一部分记录的关键字均比另一部分小,再分别对这两部分进行快速排序,以达到整个序列有序。通常取第一个记录的值为基准值或枢轴。
具体做法:附设两个指针low和high,初值分别指向第一个记录和最后一个记录,设枢轴为 key;
(1)从high 所指位置起向前搜索,找到第一个不大于基准值的记录与枢轴记录相互交换;
(2)从low 所指位置起向后搜索,找到第一个不小于基准值的记录与枢轴记录相互交换。
(3)重复这两步直至low=high为止。
![](https://oscdn.geek-share.com/Uploads/Images/Content/202009/03/f9b3f2f9446cd369287f177fde5f3de6)
![](https://oscdn.geek-share.com/Uploads/Images/Content/202009/03/f8e06fa0584be5ac8b723c88af909f93)
最坏的情形(每次能划分成两个子区间,但其中一个是空),快速排序的最坏时间复杂度为O(n^2),退化成冒泡排序。
对n较大的情况,它是平均速度最快的排序算法,但当n很小时,此方法往往比其他简单排序方法还要慢。
快速排序是不稳定的。
1.冒泡排序
1.1基本思想
小的浮起,大的沉底具体做法:
第一趟:第1个与第2个比较,大则交换;第2个与第3 比较,大则交换,… 关键字最大的记录交换到最后一个位置上;
第二趟:对前n-1个记录进行同样的操作,关键字次大 的记录交换到第n-1个位置上;依次类推,则完成排序。
1.2代码实现
package sort.swampSort; public class BubbleSort { /** * @param args */ //冒泡排序 public static void bubbleSort(int[] L){ for(int i = L.length-1; i > 1; i--){//i控制比较的趟数,比较n-1趟 for(int j = 1; j < i; j++){ if(L[j] > L[j+1]){//交换 L[0] = L[j+1]; L[j+1] = L[j]; L[j] = L[0]; } } } } public static void main(String[] args) { // TODO Auto-generated method stub int[] test = {0, 25, 56, 49, 78, 11, 65, 41, 36}; //0号单元未使用 bubbleSort(test); for(int i = 1; i <= test.length-1; i++) System.out.print(test[i]+" "); } }运行结果:
1.3性能分析
正序:只需进行一趟排序,在排序过程中进行n-1次关键字间的比较,且不移动记录;时间复杂度为O(n) 。逆序:需要进行n-1趟排序,需要进行n(n-1)/2次比较,并作等数量级的记录移动。总的时间复杂度为O(n^2) 。
起泡排序方法是稳定的。适合于数据较少的情况。
2.快速排序
2.1基本思想
背景:起泡排序的过程可见,起泡排序是一个增加有序序列长度的过程,也是一个缩小无序序列长度的过程,每经过一趟起泡,无序序列的长度只缩小 1。试设想:若能在经过一趟排序,使无序序列的长度缩小一半,则必能加快排序的速度。基本思想:通过一趟排序将待排序列以枢轴为标准划分成两部分,使其中一部分记录的关键字均比另一部分小,再分别对这两部分进行快速排序,以达到整个序列有序。通常取第一个记录的值为基准值或枢轴。
具体做法:附设两个指针low和high,初值分别指向第一个记录和最后一个记录,设枢轴为 key;
(1)从high 所指位置起向前搜索,找到第一个不大于基准值的记录与枢轴记录相互交换;
(2)从low 所指位置起向后搜索,找到第一个不小于基准值的记录与枢轴记录相互交换。
(3)重复这两步直至low=high为止。
2.2代码实现
package sort.swampSort; public class QuickSort { /** * @param args */ //交换顺序表L的字表L[low...high]的记录,枢轴记录到为,并返回枢轴应该所在的位置 //此时,枢轴前面的记录均小于枢轴,枢轴后面的记录均大于枢轴 //是一趟快排 public static int partion(int[] L, int low, int high){ L[0] = L[low];//L[0]暂存枢轴,字表中的第一个元素一般默认为是枢轴 while(low < high){ while(low < high && L[0] <= L[high]) high--; //此时L[high]>L[0] L[low++] = L[high]; while(low < high && L[0] >= L[low]) low++; //此时L[low]>L[0] L[high--] = L[low]; } //循环结束时,一定有low==high L[low] = L[0]; return low; } //递归形似的快速排序 public static void quickSort(int[] L, int low, int high){ //对顺序表L的子序列L[low...high]做快速排序 if(low < high){ int m = partion(L, low, high); quickSort(L, low, m-1); quickSort(L, m+1, high); } //low==high时,说明子序列中仅有一个元素了,显然已经有序,应作为每一层递归的结束 } public static void main(String[] args) { // TODO Auto-generated method stub int[] test = {0, 46, 55, 13, 42, 94, 5, 17, 70}; //0号单元未使用 quickSort(test, 1, test.length-1); for(int i = 1; i <= test.length-1; i++) System.out.print(test[i]+" "); } }运行结果:
2.3性能分析
最好的情形(左、右子区间的长度大致相等),快速排序的最好时间复杂度应为O(nlog2n)。最坏的情形(每次能划分成两个子区间,但其中一个是空),快速排序的最坏时间复杂度为O(n^2),退化成冒泡排序。
对n较大的情况,它是平均速度最快的排序算法,但当n很小时,此方法往往比其他简单排序方法还要慢。
快速排序是不稳定的。
相关文章推荐
- 学习数据结构和算法动态可视化工具
- 数据结构 第一章 绪论
- 【面试经典题之字符串】实现一个算法,确定一个字符串的所有字符是否全都不同。假设不允许使用额外的数据结构
- 数据结构(23)--排序篇之插入排序
- Android Binder机制(二) Binder中的数据结构
- R语言中的数据结构
- 阿里巴巴实习内推二面经验总结(客户端开发岗)
- 2015年大二上-数据结构-查找-2-(1)-HashTable
- 数据结构笔记——
- 【数据结构】线性表(数组实现)
- 小蚂蚁学习数据结构(35)——直接插入排序
- 简单数据结构(三)栈
- 数据结构与算法学习笔记(四)
- 数据结构之“Ordered List and Sorted List”(六)
- 数据结构与算法笔记 —— 向量
- 数据结构与算法笔记 —— 排序算法及代码实现
- bzoj1012[最大数]
- 《数据结构》链栈
- 《数据结构》顺序栈
- 最小堆建立