一直都听说快排是一种极其优秀的排序算法,到底有多优秀呢,今天,一起探究一下。
一、原理讲解
探究算法的最终目的是为了利用编程解决问题,编程的前提就要弄清楚快排的原理,网上对于快排的说法都很专业,各类的词汇堆叠,显得格外的高大上,甚至高大到让人抵触,还没学习,就已经被吓到了,其实,快排的原理特别的简单:
从需要排序的数里面找出一个数,然后,把比这个数小的放在这个数左边,比这个数大的放在这个数右边,一样大的和这个数放在一起,最后,左右两边各自重复上述过程,直到左边或右边只剩下一个数(或零个数)无法继续为止。
根据此原理,举个例子来说明: 对于int [] array={30,1,40,2,4,35 }
(1)选取第一个数30作为基准数,把小于30的数放在30的左边,为 4 1 2 30
(2)把大于30 的数放在30 的右边,为 30 40 35
这样数组array就变成了 4 1 2 30 40 35 以30作为分界点就划分为了两部分,记做左侧数组{ 4 1 2 }和右侧数组{ 40 35}
(3)对左侧数组和右侧数组分别重复上面的操作(选取一个数作为基准,小的放左,大的放右):
左侧数组为 2 1 4 ->1 2 4 右侧数组为 35 40
(4)整体的输出为1 2 4 30 35 40
(5)快速排序完成。
二、编程实现
弄清楚原理之后,就需要利用编程来实现啦!
首先,分析一下,由于左侧数组和右侧数组会重复一个步骤,因此会用到递归;
其次,循环的使用是不可能避免的,因为要从左往右或者从右向左的查找比基准数大或者小的数。
时间的复杂度,最差情况下,n个数据全部走完,O(n^2); 最好的情况下,一半的需要,nlogn。
准备好键盘,编程要开车了。。。
由于个人语言的方便,此处的代码采用Java来实现
import java.util.Arrays;
public class Quick{
public static void main(String[] args){
Integer a[] = {30, 1, 40, 2, 4, 35};
QuickSort(a, 0, a.length-1);
System.out.println(Arrays.toString(a));
}
public static void QuickSort(Integer [] array, int l, int r){//此处的l和r是数组的第一书记和最后一个数的下标。
if(l>=r){
return ;//递归结束的标志
}
int k= array[l];//从数组中取出一个数,最为基准,此处去除l下标对应的数。
int left=l; int right=r;//次数和下标赋值给left和right两个临时变量,其实就是两个指针,一个在左侧,一个在右侧。
while(left<right)//指针走起来{
while(right>left && array[right]>=k){//此处是right指针在从后右往左一步一步的走,寻找比基准值K小的数,while中的条件 // 是 大于等于,一旦找到小于k的值,跳出循环
right--;
}
array[left]=array[right];//把小于k 的值赋值给left对应的数,其实就是l对应的位置上的数,不用担心此数的缺失,已经保存在 //了k 中
while(left<right && array[left]<=k){
left++;
}
array[right]=array[left];
}
array[left]=k;//把k值填上,现在的数组已经分成了以K为分界线的左右两数组(逻辑上,物理上还是一个数组)
//左右两个数组重复实现指针移动划分数的功能,采用递归
QuickSort(array, l, left);//左侧数组,含k
QuickSort(array, left+1, r);//右侧数组
}
}
好了,代码已经编写完毕了,对于代码中出现的问题,(可能会有),没有经过编译器,直接就上手敲了,读者在使用的过程中,还是自己动手编写一遍,理解其中的含义,写过两遍以后,对于算法的理解就会有不同程度的加深哦!
母亲节的日子里,也希望在优快云里学习、分享经验的小伙伴们,抽出时间给家里打个电话或者陪在妈妈身边,说出你最想对妈妈说的话;坐在沙发上聊一聊小时候的事情,肯定会有很多美好的回忆,欢声笑语,想象一下这个场景,真的是好幸福!