数据结构——快速排序

数据结构——快速排序

​ 排序算法中的快速排序应该是赫赫有名了,代码简单,效率却十分的高。它是一种改进的冒泡算法。同样是通过依次比较两个数字然后交换位置,这一点是相同的,但是冒泡算法是相当效率低的,原因是它进行了很多不必要的比较和交换,比如:你若是为了将第一个数字下沉到最后的位置,从而移动了所有的数字,并且这些移动对其他数字而言是毫无意义的,从而诞生了快速排序。可以它每次排一个数字,这一点是从来没变过的,和冒泡算法相比。但是他移动不是盲目的比较。而是将它移动到自己的位置,并且使其他的的数字满足以下规律:比它大的数字在它的右边,比它小的数字在它的右边。仅此而已。这样子花费的时间不会比冒泡式的移动花费多余的时间的。移动的方法是如下:

比如对于以下数组 a r r a y array array

4938659776132749
12345678

1.选择一个你希望移动的数字,比如第一个49;

2。保存它 k e y = 49 key=49 key=49 b e g a n began began = 1 e n d end end= 8,后面你会知道为什么保存它的。

3选择一个数字和它比较大小,方法是从后面依次向前面扫描,找到第一个比它小的数字 m i n min min,这个数字毫无疑问是需要我们移动的。所以 m i n min min 的位置需要移动到一个地方,明显移动到 a r r a y [ 1 ] array[1] array[1] 就很合适,因为这个地方的数字不再49了。 e n d − − end-- end

4.再从前面扫描找到一个比 k e y key key 大的数字,把它换到一个新的位置,最好的选择是之前那个比 k e y key key 小的数字的位置,因为那个位置不再是它了,而且它相对偏后面。 b e g a n − − began-- began

重复上面3,4步骤,你可以发现会发现扫描到 b e g a n = e n d began=end began=end 意思代表位置交换结束了,已经没有需要变动的其他元素了,当前的 b e g a n began began 他前面的数字都比 k e y key key 小,后面的数字都比 k e y key key 大,这个位置就是 k e y key key 应该在的位置。

上面排序后剩下两个部分的元素是无序的,我们同样对这两个部分的元素使用上述相同方法。又可以排好两个数字到自己应该的位置。周而复始的递归下去。直到每个部分只包含一个元素就代表排序完成了,所有的序列都是有序的。

演示如下:

key=49

4938659776132749
12345678

在后面找到

12345678
273865977613#2749s=1 e=7
2738#659776136549s=3 e=7
2738139776#136549s=3 e=6
273813#9776976549s=4 e=6
273813#9776979549s=4 e=4
2738134976979549

上述交换和文字描述的是一致的。

49是第一个排好的数字,接下的就是对2713和7697进行上述操作。迭代至每个待排的序列长度为一结束。

学习算法不论是简单的算法还是复杂的算法,如果觉得有困难的话,我觉得画图是一个很好的理解方法。快速排序不算什么复杂算法。而且也并不需要自己手写。但对学习能力培养是不错的。吾日三省我身,就是这么一回事了。

上代码:

#include <iostream>
#include<cstdio>
#include <cstring>
using namespace std;


void quicksort(int a[],int s,int e)
{
    if(s>=e) return;
    int key =a[s];
    int l=s,r=e;
    while(s<e)
    {
        while(s<e && a[e]>=key)
            e--;
        a[s] = a[e];
        while(s<e && a[s]<=key)
            s++;
        a[e]=a[s];
    }
    a[e]=key;
    quicksort(a,l,e-1);
    quicksort(a,e+1,r);
}
int main()
{
    int a[10] = {49,68,65,97,76,13,27,49};
    quicksort(a,0,7);
    for(int i=0;i<7;i++)
        printf("%d ",a[i]);
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值