亲历快速排序算法,有感于程序的边界条件
2014-12-04 02:05
162 查看
看数据结构的书,关于快速排序.算法倒是不难理解. 网上随便baidu了一个算法. 看起来似乎也像那么回事.
然而原程序中只对10个数排序,并且排序前的数组的元素的值和顺序已经确定. 改成用java.util.Random产生随机数,来运行, 此时发现程序陷入死循环的几率非常大,即使没有死循环, 排序的结果也不对.
于是改一改吧.. 发现连界情况很是微妙. 也是本人愚钝,加上晚上思路不清,有些迷糊, 改了大约两个小时才改好.
现在随机数的上限和数组的大小均可以由参数指定 ,如果随机数的上限和数组的大小接近,可以考验程序在数组中有多个重复值时的运行情况;程序运行完后会打印出比较次数和交换次数.
具体边界情况我都加上了注释.
然而原程序中只对10个数排序,并且排序前的数组的元素的值和顺序已经确定. 改成用java.util.Random产生随机数,来运行, 此时发现程序陷入死循环的几率非常大,即使没有死循环, 排序的结果也不对.
于是改一改吧.. 发现连界情况很是微妙. 也是本人愚钝,加上晚上思路不清,有些迷糊, 改了大约两个小时才改好.
现在随机数的上限和数组的大小均可以由参数指定 ,如果随机数的上限和数组的大小接近,可以考验程序在数组中有多个重复值时的运行情况;程序运行完后会打印出比较次数和交换次数.
具体边界情况我都加上了注释.
import java.util.Random; /** * 快速排序 通过一趟排序将要排序的数据分割成独立的两部分, 其中一部分的所有数据都比另外一部分的所有数据都要小, * 然后再按此方法对这两部分数据分别进行快速排序, 整个排序过程可以递归进行,以此达到整个数据变成有序序列。 * */ public class QuickSort { private static int compareTime = 0; private static int swapTime = 0; public static void main(String[] args) throws Exception { int size = 15; int sead = 20; if (args.length < 2) { System.out .println("下次请输入两个参数,第一个为数组的大小,第二个为随机数的上限,例如 java QuickSort 15 20"); System.out.println("现在程序以size=15,sead=20以运行"); } else { size = Integer.valueOf(args[0]); sead = Integer.valueOf(args[1]); } Random ran = new Random(); int[] sort = new int[size]; for (int i = 0; i < size; i++) { sort[i] = ran.nextInt(sead); } System.out.print("排序前的数组为"); for (int i : sort) { System.out.print(i + " "); } quickSort(sort, 0, sort.length - 1); System.out.println(); System.out.print("排序后的数组为"); for (int i : sort) { System.out.print(i + " "); } System.out.println("\n程序比较次数-->"+compareTime+"\n程序交换次数-->"+swapTime); } /** * 快速排序 * * @param sort 要排序的数组 * @param start 排序的开始座标 * @param end 排序的结束座标 */ public static void quickSort(int[] sort, int start, int end) { // 此时说明已经排序完成 if (end - start <= 0){ compareTime++; return; } // 设置关键数据key为要排序数组的第一个元素, // 即第一趟排序后,key右边的数全部比key大,key左边的数全部比key小 int key = sort[start]; // 设置数组左边的索引,往右移动判断比key大的数 int i = start + 1; //注意此处要加上1 // 设置数组右边的索引,往左移动判断比key小的数 int j = end; // 如果左边索引比右边索引小,则还有数据没有排序 while (i <= j) { //等号用于当只有两个元素比如 0,6的排序,如果不加等号,排序后会交换0和6从而产生错误. while (sort[j] >= key && j > start) { //这里如果去掉等号,程序即可能会产生while死循环 j--; compareTime++; } while (sort[i] < key && i < end) { i++; compareTime++; } if (i < j) { int temp = sort[i]; sort[i] = sort[j]; sort[j] = temp; swapTime++; } else { break; // 如果i>=j 说明j的位置即是key要交换的位置.交换后j前的元素均比key小,j后均比key大 } } // 此时j停留在需要交换的位置,i的位置不定,可能比j大也可能和j相等 // 将sort[start]和sort[j]交换 sort[start] = sort[j]; sort[j] = key; swapTime++; // 递归调用 if (j >= start && j <= end) { //如果去掉这两个等号 对于48,37,35,36这种情况便无法正确排序 swapTime+=2; quickSort(sort, start, j - 1); quickSort(sort, j + 1, end); } } }
相关文章推荐
- 写程序到底需不需要懂数学?有感
- 用vs .net 2005 beta2开发简单smtp邮件程序有感
- 读《用C语言编写Socket程序》有感
- 阅读《C 风格的内存分配程序》有感
- 第一个MFC程序编译有感
- 【吾悟】《易经》有感程序人生
- 中断处理程序、中断上下文中处理延时及一些函数的调用规则(调IIC中断驱动有感)
- 我的程序员之路(四)-----校研究生处投票网站有感 分类: 程序人生 2012-04-04 22:59 904人阅读 评论(0) 收藏
- 学编程、写程序有感
- 快速排序算法程序
- 用c++写msp430程序有感
- 脾气与冲突--试用ymlf下wine跑windows程序有感
- 做applet程序之有感
- 亲历2008 Tech•Ed 有感(多图)
- 情有千千劫,有感于程序编码的质量(一)
- 情有千千劫,有感于程序编码的质量(三)
- MFC 基于对话框 程序的打包有感!!!
- VS使用有感——MFC程序移植至其他PC上出现的错误
- 第一个MFC程序编译有感
- 由July师兄二分查找代码及编程珠玑有感:循环不变性(断言)证明程序的正确性及发现bug