`

快速排序算法

阅读更多
[size=small]排序是数据处理领域一种最常用的运算,排序的目的主要是为了快速查找。
常用的算法有:选择排序、快速排序、希尔排序、堆排序、冒泡排序、插入排序、归并排序。
其中选择排序、快速排序、希尔排序、堆排序不是稳定的排序算法,而冒泡排序、插入排序、归并排序和基数排序是稳定的排序算法。
其中这些排序算法中,以快速排序和二路归并排序效率较高,并且在面试时稍微深入算法面试官都会问到的。本次博文讲解快速排序。

快速排序
快速排序由于排序效率在同为O(N*logN)的几种排序方法中效率较高,因此经常被采用,再加上快速排序思想----分治法也确实实用,因此很多软件公司的笔试面试,包括像腾讯,微软等知名IT公司都喜欢考这个,还有大大小的程序方面的考试如软考,考研中也常常出现快速排序的身影。
总的说来,要直接默写出快速排序还是有一定难度的,因为本人就自己的理解对快速排序作了下白话解释,希望对大家理解有帮助,达到快速排序,快速搞定。



快速排序是C.R.A.Hoare于1962年提出的一种划分交换排序。它采用了一种分治的策略,通常称其为分治法(Divide-and-ConquerMethod)。

该方法的基本思想是:

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

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

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



虽然快速排序称为分治法,但分治法这三个字显然无法很好的概括快速排序的全部步骤。因此我的对快速排序作了进一步的说明:挖坑填数+分治法:

举例来说,现在有一个数据集{85, 24, 63, 45, 17, 31, 96, 50},怎么对其排序呢?
第一步,选择中间的元素45作为"基准"。(基准值可以任意选择,但是选择中间的值比较容易理解。)

第二步,按照顺序,将每个元素与"基准"进行比较,形成两个子集,一个"小于45",另一个"大于等于45"。

第三步,对两个子集不断重复第一步和第二步,直到所有子集只剩下一个元素为止。





参考网上和书上的资料,得出如下代码:
注意:我这里代码中为了简单起见,让第一个元素值为基准值。
代码方法:
/**
     * 快速排序算法,完成一次区间划分,返回中间位置j
     * 时间复杂度O(Nlog₂N)其中N为数组长度
     * @param a
     * @param s
     * @param t
     * @return
     */
    public static int partition(Object[] a, int s, int t) {
        // 1、给i,j赋初值
        int i = s;
        int j = t;
        // 2、将基准元素的值赋给临时变量,并让i++
        Object x = a[i++];
        // 3、i<=j时,依次检查需要进行交换位置的元素
        while(i <= j) {
            // 从前向后进行顺序查找一个大于基准值的元素,该元素需要与后面的区间中的某一个元素交换位置
            while(i <= j && ((Comparable)a[i]).compareTo(x) <= 0) {
                i++;
            }
            // 从后向前进行顺序查找一个小于基准值的元素,该元素需要与前面的区间中的某一个元素交换位置
            while(j >= i && ((Comparable)a[j]).compareTo(x) >= 0) {
                j--;
            }
            // 当条件成立时,交换a[i],a[j]的位置
            if (i < j) {
                Object temp = a[i];
                a[i] = a[j];
                a[j] = temp;
                i++;
                j--;
            }
        }
        // 交换a[s]与a[j]的值
        a[s] = a[j];
        a[j] = x;
        return j;
    }

    /**
     * 递归调用快速排序算法进行排序,本质上是分治的思想
     * @param a
     * @param s
     * @param t
     */
    public static void quickRecursion(Object[] a, int s, int t) {
        // 进行第一次快速排序
        int j = partition(a, s, t);
        // 对左区间进行快速排序
        if(s < j - 1) {
            quickRecursion(a, s, j-1);
        }
        // 对右区间进行快速排序
        if(j + 1 < t) {
            quickRecursion(a, j+1, t);
        }
    }
    
    /**
     * 主函数测试
     * @param args
     */
    public static void main(String[] args) {
        Object[] a1 = {8,9,4,3,5,7,2,1};
        System.out.println("初始数组:" + Arrays.toString(a1));
        quickRecursion(a1, 0, a1.length-1);
        System.out.println(Arrays.toString(a1));
    }


运行结果:
初始数组:[8, 9, 4, 3, 5, 7, 2, 1]
经过排序后:[1, 2, 3, 4, 5, 7, 8, 9]


在快速排序中,若把基准元素看做根结点,若把划分得到的左区间和右区间看做根结点的左子树和右子树,那么整个排序过程就对应着一棵具有n个元素的二叉搜索树。在快速排序中,记录的移动次数通常小于记录的比较次数。时间复杂度为[O(N*logN),O(n²)],空间复杂度为[O(log₂N),O(n)]。
大量的实践证明:当n较大时,它是目前为止平均情况下速度最快的一种排序算法。平均情况下,快速排序的比较次数为理想情况的2ln2≈1.39倍,所以平均的时间复杂度仍然为
O(log₂N)。

注意:快速排序不适用与基本有序的无序表。
当然,为了避免这种情况发生,也可以修改快速排序算法,每次划分前比较当前区间的第一个元素,中间元素和最后一个元素的值,取中间值为基准元素,这样就可以避免快速排序沦为简单排序了


参考:
《数据结构使用教程Java语言描述》徐孝凯
http://www.ruanyifeng.com/blog/2011/04/quicksort_in_javascript.html
http://blog.csdn.net/morewindows/article/details/6684558

[/size]
  • 大小: 3.1 KB
  • 大小: 3.5 KB
  • 大小: 3.6 KB
  • 大小: 4.2 KB
  • 大小: 3.7 KB
  • 大小: 3 KB
分享到:
评论

相关推荐

    快速排序算法相关分析

    快速排序算法相关分析 快速排序算法是一种有效的排序算法,虽然算法在最坏的情况下运行时间为 O(n^2),但由于平均运行时间为 O(nlogn),并且在内存使用、程序实现复杂性上表现优秀,尤其是对快速排序算法进行随机化...

    FPGA并行快速排序算法-位宽可设

    在本文中,我们将深入探讨基于FPGA的并行快速排序算法,特别关注“位宽可设”的特性。这种算法能够高效地处理大量数据,并且在硬件实现上具有很高的灵活性。我们将从以下几个方面来阐述这个主题: 一、快速排序算法...

    快速排序算法以及归并算法

    ### 快速排序算法 快速排序是一种高效的排序算法,采用分而治之的策略,其核心思想是选择一个基准元素,通过一趟排序将待排序的数据分割成独立的两部分,其中一部分的所有数据都比另一部分的所有数据都要小,然后再...

    快速排序算法matlab

    ### 快速排序算法在MATLAB中的应用与理解 #### 一、快速排序算法简介 快速排序是一种非常高效的排序算法,由英国计算机科学家托尼·霍尔(Tony Hoare)于1960年提出。它采用分治策略来把一个序列分为较小的两个子...

    C语言实现快速排序算法

    快速排序算法,C语言 快速排序(Quicksort)是对冒泡排序的一种改进。由C. A. R. Hoare在1962年提出。它的基本思想是:通过一趟排序将要排序的数据分割成独立的两部分,其中一部分的所有数据都比另外一部分的所有...

    c语言 数据结构 快速排序算法

    c语言版本的数据结构的快速排序算法,适用于新手学习

    快速排序算法实现

    快速排序算法C语言实现,快排序算法QuickSort.cpp

    快速排序算法实现 c#代码

    ### 快速排序算法在C#中的实现 #### 一、快速排序算法简介 快速排序是一种高效的排序算法,由英国计算机科学家托尼·霍尔(Tony Hoare)于1960年提出。该算法采用分治策略来把一个序列分为较小的两个子序列,再对这...

    快速排序算法java代码

    "快速排序算法java代码" 快速排序算法是由Tony Hoare在1960年提出的一种排序算法,它的平均时间复杂度为O(n log n),是目前最快的排序算法之一。下面我们将详细地讲解快速排序算法的java代码实现。 快速排序算法的...

    严蔚敏快速排序算法的伪代码。。。。。

    根据提供的标题、描述、标签及部分内容,我们可以梳理出与快速排序算法相关的关键知识点。 ### 快速排序算法概述 快速排序是一种高效的排序算法,在实际应用中,它的平均性能通常优于其他时间复杂度为 \(O(n\log n...

    分别使用Java和Python实现快速排序算法.zip

    快速排序:分别使用Java和Python实现快速排序算法.zip 快速排序:分别使用Java和Python实现快速排序算法.zip 快速排序:分别使用Java和Python实现快速排序算法.zip 快速排序:分别使用Java和Python实现快速排序算法....

    C++快速排序算法程序

    C++快速排序算法程序,用于处理大量数据, 并对这些数据进行快速的排序

    改进的快速排序算法

    快速排序算法的改进思路 1.选取好的基准,是两边的数据个数尽量的均匀 取数组的第一个,中间,最后一个数据,取三个数中第二大的数作为基准 2. 不递归 3.与插入结合,当段内的数组个数小于等于16的时候,使用...

    快速排序算法 C语言实现

    快速排序算法 C语言实现 快速排序算法是一种高效的排序算法,通过递归的方式将记录分区排序。下面将详细介绍快速排序算法的实现细节。 首先,我们需要了解快速排序算法的基本思想。快速排序算法的核心思想是选择一...

    Java实现快速排序算法+编程知识+技术开发

    Java实现快速排序算法+编程知识+技术开发; Java实现快速排序算法+编程知识+技术开发; Java实现快速排序算法+编程知识+技术开发; Java实现快速排序算法+编程知识+技术开发; Java实现快速排序算法+编程知识+技术...

    快速排序算法和冒泡排序效率对比

    快速排序和冒泡排序是两种常见的排序算法,它们在计算机科学中扮演着重要的角色,特别是在数据处理和优化程序性能方面。本篇文章将深入探讨这两种排序算法的原理、效率以及它们在C#编程语言中的实现。 首先,让我们...

    matlab 实现快速排序算法_一共有主程序,分类,插入和选择四个程序

    资源名:matlab 实现快速排序算法_一共有主程序,分类,插入和选择四个程序 资源类型:matlab项目全套源码 源码说明: 全部项目源码都是经过测试校正后百分百成功运行的,如果您下载后不能运行可联系我进行指导或者...

    超快速排序算法,性能优于快速排序算法和基数排序算法

    ### 超快速排序算法详解 #### 一、引言 在计算机科学中,排序算法是一种重要的基础算法,被广泛应用于各种系统软件和应用软件之中。传统的排序算法如快速排序和基数排序各有优缺点:快速排序算法因其简洁的结构和...

    一个不会出现堆栈溢出的快速排序算法

    总的来说,采用循环法的快速排序算法解决了递归版本可能导致的堆栈溢出问题,且在处理大型随机数组时能保持良好的效率。通过对数组的巧妙分区和基准元素的随机选取,该算法在实际应用中表现出色。文件"cishi"可能...

Global site tag (gtag.js) - Google Analytics