分别使用递归和迭代实现快速排序

    #include<iostream>
    #include<stack>
    #include<ctime>
    #include"CaculateTime.h"
    using namespace std;
    /*
       递归算法,使用 刘大有《数据结构》第二版 里的算法
    */
    void QuikSort(int(&a)[100], int low, int high)
    {
        if (low < high)
        {
            int front = low;
            int back = high + 1;
            int item = a[low];
            while (front < back)
            {
                front++;
                while (a[front] < item)
                    front++;
                back--;
                while (a[back] > item)
                    back--;
                if (front < back)
                    swap(a[front], a[back]);
            }
            swap(a[low], a[back]);
            QuikSort(a, low, back - 1);
            QuikSort(a, back + 1, high);
        }
    }
    /*
      在QuikSort基础上写了个迭代法,结果反而比QuikSort慢
    */
    void QuikSort_iteration(int(&a)[100], int n)  
    {
        stack<int> s;
        s.push(0); //low
        s.push(n); //high
        while (!s.empty())
        {
            int low;
            int high;
            high = s.top();
            s.pop();
            low = s.top();
            s.pop();

            if (low < high)
            {

                int left = low;
                int right = high;
                int item = a[low];
                while (left < right)
                {
                    left++;
                    while (a[left] < item)
                        left++;
                    right--;
                    while (a[right] > item)
                        right--;
                    if (left < right)
                        swap(a[left], a[right]);
                }
                swap(a[low], a[right]);
                //保存参数
                s.push(right + 1);
                s.push(high);
                s.push(low);
                s.push(right - 1);
            }
        }
    }
    /*
       改进迭代,减少了对栈的操作,速度更快但还是比递归慢很多
       据说是因为 STL的栈不适合用在这。。。。
       */
    void QuikSort_iteration_EX(int(&a)[100], int n)
    {

        stack<int> s;
        s.push(0); //low
        s.push(n); //high
        while (!s.empty())
        {
            int low;
            int high;
            high = s.top();
            s.pop();
            low = s.top();
            s.pop();

            while (low < high)
            {

                int left = low;
                int right = high;
                int item = a[low];
                while (left < right)
                {
                    left++;
                    while (a[left] < item)
                        left++;
                    right--;
                    while (a[right] > item)
                        right--;
                    if (left < right)
                        swap(a[left], a[right]);
                }
                swap(a[low], a[right]);
                //保存参数
                if (right - low < high - right)  //前部分较小
                {
                    //保存后部分
                    s.push(right + 1);
                    s.push(high);
                    high = right - 1;
                }
                else
                {
                    s.push(low);
                    s.push(right - 1);
                    low = right + 1;
                }
            }
        }
    }
    /*
       非递归终极改进版,自己实现栈,速度比递归的快!!!
       */
    void QuikSort_iteration_EX_EX(int(&a)[100], int n)
    {
        int myStack[100];
        int top = -1;
        myStack[++top] = 0; //low   ++top:先top=top+1;再取top的值
        myStack[++top] = n; //high

        while (top != -1)
        {
            int low;
            int high;
            high = myStack[top--];  // top--:先取top的值;再top=top-1
            low = myStack[top--];

            while (low < high)
            {

                int left = low;
                int right = high;
                int item = a[low];
                while (left < right)
                {
                    left++;
                    while (a[left] < item)
                        left++;
                    right--;
                    while (a[right] > item)
                        right--;
                    if (left < right)
                        swap(a[left], a[right]);
                }
                swap(a[low], a[right]);
                //保存参数
                if (right - low < high - right)  //前部分较小
                {
                    //保存后部分
                    myStack[++top] = right + 1;
                    myStack[++top] = high;
                    high = right - 1;
                }
                else
                {
                    myStack[++top] = low;
                    myStack[++top] = right - 1;
                    low = right + 1;
                }
            }
        }
    }
    int main()
    {
        //  int n = 20;
        //  int a[100] = { 2, 4, 6, 23, 7, 4, 8, 13, 56, 467, 3, 9, 56, 24, 56, 4, 58, 23, 12, 0 };

        int n = 100;
        int a[100];

        MyRandom::g_srand();
        for (int i = 0; i < 100; i++)
            a[i] = MyRandom::g_random_int(0, 100);

        CaculateTime caculateTime;
        caculateTime.Init();
        QuikSort(a, 0, n - 1);
        double time1 = caculateTime.getDeltaTime();
        cout << "递归时间: " << time1 << " us" << endl;

        //打乱顺序
        for (int i = 0; i < 100; i++)
            a[i] = MyRandom::g_random_int(0, 100);
        caculateTime.Init();
        QuikSort_iteration(a, n);
        double time2 = caculateTime.getDeltaTime();
        cout << "迭代时间: " << time2 << " us" << endl;

        //打乱顺序
        for (int i = 0; i < 100; i++)
            a[i] = MyRandom::g_random_int(0, 100);
        caculateTime.Init();
        QuikSort_iteration_EX(a, n);
        double time3 = caculateTime.getDeltaTime();
        cout << "迭代_改进版时间: " << time3 << " us" << endl;

        //打乱顺序
        for (int i = 0; i < 100; i++)
            a[i] = MyRandom::g_random_int(0, 100);
        caculateTime.Init();
        QuikSort_iteration_EX_EX(a, n);
        double time4 = caculateTime.getDeltaTime();
        cout << "迭代_终极改进版时间: " << time4 << " us" << endl;

        cout << "排序后:" << endl;
        for (int i = 0; i < n; i++)
            cout << a[i] << " ";
        cout << endl;
        return 0;
    }

运行结果:迭代算法还是比较快的
运行结果

其中CaculateTime.h文件内容

#pragma once
#include<Windows.h>

class CaculateTime
{
public:
    static void Init();
    static double getDeltaTime() //单位微秒
    {
        QueryPerformanceCounter(&liPerfEnd);
        double dfTime = (double)liPerfEnd.QuadPart - liPerfStart.QuadPart;
        double deltaTime = dfTime * 1000 * 1000 / liPerfFreq.QuadPart; //单位微秒
        return deltaTime;
    }
private:
    static LARGE_INTEGER liPerfFreq;
    static LARGE_INTEGER liPerfStart;
    static LARGE_INTEGER liPerfEnd;
};
LARGE_INTEGER CaculateTime::liPerfFreq = { 0 };
LARGE_INTEGER CaculateTime::liPerfStart = { 0 };
LARGE_INTEGER CaculateTime::liPerfEnd = { 0 };
void CaculateTime::Init()
{
    QueryPerformanceFrequency(&liPerfFreq);
    QueryPerformanceCounter(&liPerfStart);
}
namespace MyRandom
{
    void g_srand()
    {
        srand(unsigned(time(0)));
    }
    double g_random_double(double start, double end)
    {
        return start + (end - start)*rand() / (RAND_MAX + 1.0);
    }
    int g_random_int(int start, int end)
    {
        return start + (end - start)*rand() / (RAND_MAX + 1);
    }
};
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值