快速排序

本文介绍了快速排序算法,其基本思想是先取基准数,将比它大的数放右边,小的或相等的放左边,再对左右区间重复操作。详细说明了排序步骤和代码实现思路,还分析了优缺点,指出其平均性能好,但最坏情况与插入排序相同,数据量大于20时性能佳。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

快速排序的基本思想:

1、先从序列中取出一个数作为基准数。

2、区分过程,把比这个数大的数全部放到它的右边,小于它的或等于它的数放到左边。

3、再对左右区间重复第二步,直到个个区间只有一个数。

 

快速排序详细步骤:

以一个数组作为示例,取区间第一个数为基准数。

初始时,i = 0;  j = 9;   X = a[i] = 72

由于已经将a[0]中的数保存到X中,可以理解成在数组a[0]上挖了个坑,可以将其它数据填充到这来。

从j开始向前找一个比X小或等于X的数。当j=8,符合条件,将a[8]挖出再填到上一个坑a[0]中。a[0]=a[8]; i++;  这样一个坑a[0]就被搞定了,但又形成了一个新坑a[8],这怎么办了?简单,再找数字来填a[8]这个坑。这次从i开始向后找一个大于X的数,当i=3,符合条件,将a[3]挖出再填到上一个坑中a[8]=a[3]; j--;

数组变为:

i = 3;   j = 7;   X=72

再重复上面的步骤,先从后向前找,再从前向后找。

从j开始向前找,当j=5,符合条件,将a[5]挖出填到上一个坑中,a[3] = a[5]; i++

从i开始向后找,当i=5时,由于i==j退出。

此时,i = j = 5,而a[5]刚好又是上次挖的坑,因此将X填入a[5]。

数组变为:

代码实现:

        static void Main(string[] args)
        {
            int[] arr = new int[] { 5, 3, 6, 2, 4, 7 };

            QuickSort(arr,0,arr.Length - 1);
            for (int i = 0; i < arr.Length; i++)
            {
                Console.Write(arr[i] + " ");
            }
            Console.ReadKey();
        }  

        private static void QuickSort(int[] arr,int left,int right)
        {
            if(left < right)
            {
                int x = arr[left];         // 基准数,把比这个数大的数全部放到它的右边,小于它的或等于它的数放到左边。
                int i = left;
                int j = right;

                while(i < j)
                {
                    while(i < j)
                    {
                        if(arr[j] <= x)         // 找到一个小于等于基准数的数把它放再x的左边
                        {
                            arr[i] = arr[j];    // 将比基准数小的数放到空出来的位置
                            break;
                        }
                        else
                        {
                            j--;               // 像左移动继续查找,做比较
                        }
                    }

                    while(i<j)
                    {
                        if (arr[i] > x)         // 找到一个大于基准数的数 把它放再x的又
                        {
                            arr[j] = arr[i];  
                            break;
                        }
                        else
                        {
                            i++;               // 像右查找继续,继续做比较
                        }
                    }
                }

                // 跳出循环 i == j 的时候 责 i 是中间位置
                arr[i] = x;                     // 一轮结束后找到了基准数的位置  然后将数组分成了两个区间   left 到 i - 1 和 i + 1 到 right
                QuickSort(arr,left,i-1);
                QuickSort(arr,i+1,right);
            }
        }

快排总结

1.i =L; j = R; 将基准数挖出形成第一个坑a[i]。

2.j--由后向前找比它小的数,找到后挖出此数填前一个坑a[i]中。

3.i++由前向后找比它大的数,找到后也挖出此数填到前一个坑a[j]中。

4.再重复执行2,3二步,直到i==j,将基准数填入a[i]中。

快速排序优缺点

       快速排序具有最好的平均性能(average behavior),但最坏性能(worst case behavior)和插入排序相同,也是O(n^2)。比如一个序列5,4,3,2,1,要排为1,2,3,4,5。按照快速排序方法,每次只会有一个数据进入正确顺序,不能把数据分成大小相当的两份,很明显,排序的过程就成了一个歪脖子树,树的深度为n,那时间复杂度就成了O(n^2)。尽管如此,需要排序的情况几乎都是乱序的,自然性能就保证了。据书上的测试图来看,在数据量小于20的时候,插入排序具有最好的性能。当大于20时,快速排序具有最好的性能,归并(merge sort)和堆排序(heap sort)也望尘莫及,尽管复杂度都为nlog2(n)。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值