经典排序算法之快速排序(C#)

快速排序是一个对冒泡排序改进的排序。

工作原理:①、设置两个指针a和b分别指向序列的开始和最后

②、设置一个参照物(一般是第一个数),由指针b指向的数与参照数进行比较,如果指针指向的数比参照数大,指针左移。如果如果指针指向的数比参照数小,交换他们两个的位置并由指针a操作。

③、由指针a指向的数与参照数进行比较,如果指针指向的数比参照数小,指针右移。如果如果指针指向的数比参照数大,交换他们两个的位置并由指针b操作。

④、在保证指针a<b的同时,重复②、③操作。

看代码:

    class Program
    {
        static void Main(string[] args)
        {
            int[] arr = { 12, 3, 456, 21, 7, 32, 43 };
            int a = 0, b = arr.Length - 1;
            QuickSort(arr,a,b);
            for (int i = 0; i < arr.Length; i++)
            {
                Console.Write(arr[i] + "  ");
            }
        }

        public static void QuickSort(int[] arr,int a,int b)
        {
            //如果开始的索引已经大于结束的索引,说明已经排序完成
            if (a >= b)
            {
                return;
            }
            int i = a, j = b;
            int sum = arr[i];//将序列中的第一个数设置为参照数

            //保证右侧索引大于左侧索引,如果不大于时就证明整个序列已经遍历完了
            while (i < j)
            {
                //如果参照数比在它右侧的数小,并且左侧索引小于右侧索引,那右侧索引向左推进
                while (i < j && sum <= arr[j])
                {
                    j--;
                }
                arr[i] = arr[j];    //当右侧的数比参照数小得时候,将右侧的数赋值给左侧的数(左侧的数没有消失只是被记录下来了)
                //如果参照数比在它左侧的数大,并且左侧索引小于右侧索引,那左侧索引向右推进
                while (i < j && sum >= arr[i])
                {
                    i++;
                }
                arr[j] = arr[i];
            }
            arr[i] = sum;   //该序列已经遍历完,将参照数归位(就是放到中间位置)
            //由递归的思想,遍历参照数的左右两侧
            QuickSort(arr, a, i - 1);
            QuickSort(arr, i + 1, b);
        }
    }

运行结果为:

时间复杂度分析:

最好情况下是每一次取到的元素都刚好平分整个数组,时间复杂度为O(nlogn);

最坏情况下是数组已经基本有序,每一次取到的都是最大/最小元素,这时就成了冒泡排序了,时间复杂度为O(n^2);

平均时间复杂度为O(nlogn);

算法的稳定性:快速排序在交换过程中,元素的位置会大幅度的交换,当有相同元素时排序结束后位置可能发生变化,是不稳定排序。

算法适用的场合:

快速排序是目前在所有排序算法中最好的算法(除特殊场合),当代排序的序列无序时,快速排序的平均时间最短。


猜你喜欢

转载自blog.csdn.net/qq_38721111/article/details/80395103