QuickSort排序过程(正序,左往右,小到大):
原始 int 数组 p:
下标 |
0 |
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
数字 |
6 |
1 |
5 |
8 |
7 |
6 |
4 |
5 |
2 |
4 |
i=0,j=9,k=p[i]=6(第0个数值:6)。
1. p[j] 往前匹配小于 k 的 p[j] , j=9 时,p[j] = 4<k (k=6), 将 p[j] 和 [pi] 的位置对调;
下标 |
0 |
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
数字 |
4 |
1 |
5 |
8 |
7 |
6 |
4 |
5 |
2 |
6 |
2. p[i] 往后匹配, i=3, p[i] = 8>k (k=6),将当前 p[i] 和 p[j] 的位置对调,此时 i=3, j=9;
下标 |
0 |
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
6 |
数字 |
4 |
1 |
5 |
6 |
7 |
6 |
4 |
5 |
2 |
8 |
3. 重复步骤1和步骤2,直到i和j碰头停止匹配 完成一轮排序,第一轮排序过后数组顺序为:
下标 |
0 |
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
数字 |
4 |
1 |
5 |
2 |
5 |
6 |
4 |
6 |
7 |
8 |
4. 此时i=j=7以k为分界点,左边是小于等于k的数的集合,右边是大于等于k的数的集合,将这两个集合分开按照1-4的步骤排序直到产生的子集数的元素数量小于等于1个,整个排序结束,得到排序后的结果。
下标 |
0 |
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
数字 |
1 |
2 |
4 |
4 |
5 |
5 |
6 |
6 |
7 |
8 |
C#实现:
public class QuickSort
{
public List<int> list = null;
public QuickSort(List<int> l)
{
list = l;
}
//从小到大排序
public void qs(int l, int r)
{
int i = l;
int j = r;
if (i >= j)//如果当前排序集合里面的元素个数小于2个则结束此分支的排序
{
return;
}
int key = list[i];//以集合第一个元素作为界定值
while (i < j)//排序
{
while (i < j && list[j] >= key)//从后往前匹配第一个小于界定值key的值
{
j--;
}
list[i] = list[j];//将当前j位置的值放到i处
while (i < j && list[i] <= key)//从前往后匹配第一个大于界定值key的值
{
i++;
}
list[j] = list[i];//将当前i位置的值放到j处
}
list[i] = key;//这里完成
//以key为分界将数字集合分成两个集合 递归进行下一轮排序
qs(l, i - 1);//小于等于key部分
qs(i + 1, r);//大于等于key部分
}
}
这里是单线程,用递归来切入下一轮排序,用公共的集合比以参数的形式将集合传入会节省点内存。