1.概念
快速排序(Quick Sort)是从冒泡排序算法演变而来的,实际上是在冒泡排基础上的递归分治法。快速排序在每一轮挑选一个基准元素,并让其他比它大的元素移动到数列一边,比它小的元素移动到数列的另一边,从而把数列拆解成了两个部分
2. 算法原理
这是一个无序数列:6、7、4、5、2、3、1、8,我们要将它按从小到大排序。按照快速排序的思想,我们先选择一个基准元素,进行排序。
我们选取6为我们的基准元素,并设置基准元素的位置为index,设置两个指针left和right,分别指向最左和最右两个元素
接着,从right指针开始,把指针所指向的元素和基准元素做比较,如果比基准元素大,则right指针向左移动,如果比基准元素小,则把right所指向的元素填入index中
8比6大,right指针左移
1比7小。arr[left]=arr[right]
,index = right
,同时left右移一位left++
。
然后,我们切换left指针进行比较,如果left指向的元素小于基准元素,则left指针向右移动,如果元素大于基准元素,则把left指向的元素填入index中
7比6大。arr[right]=arr[left]
,index = left
,同时right左移一位right--
。
切换right指针比较
3比6小,arr[left]=arr[right]
,index = right
,同时left右移一位left++
。
切换左指针。4,5,2都比比6小,直接右移。 最终最终left和right重合
此时,我们将基准元素填入index中,这时,基准元素左边的都比基准元素小,右边的都比基准元素大,这一轮交换结束。
第一轮,基准元素6将序列分成了两部分,左边小于6,右边大于6,第二轮则是对拆分后的两部分进行比较
根据以上原理,我们先完成这一步的代码
function partition(arr, startIndex, endIndex) {
let pivot = arr[startIndex] // 选择第一个元素为基准元素
let left = startIndex
let right = endIndex
let index = startIndex
while(right > left) {
// right指针从右向左进行比较
while(right > left) {
// 在右边一直找,直到找到小于pivot,才退出
if (arr[right] < pivot) {
arr[left] = arr[right]
index = right
left++
break
}
right--
}
// left指针从右向左进行比较
while(right > left) {
if (arr[left] > pivot) {
arr[right] = arr[left]
index = left
right--
}
left++
}
}
arr[index] = pivot
return index
}
接着,根据递归分治的思想。第一轮的得到的基准下标为5 分为两组:
- 【1,3,4,5,2】pivot为1,
partition(0, 5-1)
- 【7,8】pivot为7,
partition(5+1,7)
function quickSort(arr, startIndex, endIndex) {
if (startIndex >= endIndex) {
return
}
let pivotIndex = partition(arr, startIndex, endIndex)
// 向左递归
quickSort(arr, startIndex, pivotIndex - 1)
// 向右递归
quickSort(arr, pivotIndex + 1, endIndex)
}