快速排序法过程演示

 'Excel宏代码原创分享,转发请注明来源,作者:王欢为,WX:13772568903。

功能:演示快速排序法的排序过程。

特点:1.演示的过程实际上也是排序的过程,既能看到数字排序的过程,同时也能看到色块排序的过程。

特点:2.用来排序的数字的多少,数字的分布可以手动设置,也可以随机设置。做到随心测试。

操作:在Sub Yanshi1()中修改参数后(如果不想修改也可以不修改),点击运行,然后就可以在当前工作表中观看动画过程了。 

Dim Hang1&, Hang2&, Lie1&, Zhenshu1#, Shoudong1&, Time1#, Cha1&
Sub Yanshi1()
    'Excel宏代码原创分享,转发请注明来源,作者:王欢为,WX:13772568903。
    '演示冒泡法进行排序的过程,演示的是升序排列过程。
    Lie1 = 7 '数据所在列号,可以手动修改,Lie1最小取7
    Hang1 = 3 '数据起始行号,可以手动修改,Hang1最小取3
    Hang2 = 20 '数据末尾列号,可以手动修改
    Zhenshu1 = 5 '每秒帧数,仅供参考,可以手动修改
    Shoudong1 = 0 '是否手动输入数据,1为手动,0为自动。
    '如果手动输入数据,需要先全选excel当前工作表,删除 _
    现有数据及背景,然后在Cells(Hang1,Lie1)和Cells(Hang2,Lie1) _
    之间的单元格输入数字,留空的单元格程序会随机补充 _
    0~255之间的数字。
    Call CCYanshikuaisupaixufa
End Sub
'以上为参数设置部分,其中Lie1最少为7, _
如果给的数字小于7,运行过程中会强制改为7。
Private Sub CCYanshikuaisupaixufa()
    If Shoudong1 = 0 Then
        Cells.Delete
    End If
    Cells.Borders.LineStyle = xlContinuous '设置边框
    Dim ii&, Num1#, Num2#, Num3#, Num4&, Row1&, Row2&
    If Lie1 < 7 Then
        Lie1 = 7
    End If
    If Hang1 < 3 Then
        Hang1 = 3
    End If
    Cha1 = 4
    Time1 = 1 / Zhenshu1
    Num1 = 8.8E+307
    Num2 = -8.8E+307
    For ii = Hang1 To Hang2
        If Len(Cells(ii, Lie1)) > 0 Then
            Num3 = Val(Cells(ii, Lie1))
        Else
            Num3 = Int(Rnd(Timer) * 256)
            Cells(ii, Lie1) = Num3
        End If
        If Num1 > Num3 Then
            Num1 = Num3
        End If
        If Num2 < Num3 Then
            Num2 = Num3
        End If
    Next ii
    If Num1 < Num2 Then
        Num3 = 255.99 / (Num2 - Num1)
        For ii = Hang1 To Hang2
            Num4 = Int(Num3 * (Cells(ii, Lie1) - Num1))
            Cells(ii, Lie1 - Cha1).Interior.Color = _
                RGB(255, 255 - Num4, Num4)
        Next ii
    Else
        For ii = Hang1 To Hang2 '设置单元格底色为紫色
            Cells(ii, Lie1 - Cha1).Interior.Color = RGB(255, 0, 255)
        Next ii
    End If
    Cells(1, Lie1 - Cha1) = "快速排序法排序演示"
    Cells(2, Lie1 - Cha1) = "作者:王欢为,13772568903"
    Row1 = Hang1
    Row2 = Hang2
    Call Quicksort(Row1, Row2)
    Cells(1, Lie1) = "已完成排序。"
End Sub
Private Sub Quicksort(ByVal Xuhao1&, ByVal Xuhao2&)
    Call CCdengdai(Time1)
    Cells(Xuhao1, Lie1).Interior.Color = RGB(255, 0, 255)
    Call CCdengdai(Time1)
    Cells(Xuhao2, Lie1).Interior.Color = RGB(0, 255, 0)
    Call CCdengdai(Time1)
    If Xuhao1 < Xuhao2 Then
        If Xuhao1 = Xuhao2 - 1 Then
            If Cells(Xuhao1, Lie1) > Cells(Xuhao2, Lie1) Then
                Call CCjiaohuan(Xuhao1, Xuhao2)
                Call CCdengdai(Time1)
            End If
            Range(Cells(Xuhao1, Lie1), Cells(Xuhao2, Lie1)).Interior.Color = RGB(122, 122, 122)
        Else
            Dim ii&, jj&, Flag1&, ceshi1#, Xuhao3%, Xuhao4%
            ii = Xuhao1
            jj = Xuhao2
            '以下2行是为了增加随机性,可以一并删除。
            Flag1 = Int(Rnd(Timer) * (Xuhao2 - Xuhao1)) + Xuhao1 '该行可以删除
            Cells(1, Lie1) = "在本轮排序的数中随机找一个作为中数。比如:" & Cells(Flag1, Lie1) & "。"
            Cells(Flag1, Lie1).Interior.Color = RGB(0, 255, 255)
            Call CCdengdai(Time1)
            Cells(1, Lie1) = "将中数" & Cells(Flag1, Lie1) & "换到本轮排序的数中第一个数" & Cells(Xuhao1, Lie1) & "的位置。"
            Call CCdengdai(Time1)
            Call CCjiaohuan(Flag1, Xuhao1) '将Flag1放到数组第一位。'该行可以删除
            Cells(Flag1, Lie1).Interior.Color = RGB(255, 255, 255)
            Cells(1, Lie1) = "向上寻找小数,即<" & Cells(Xuhao1, Lie1) & "的数。"
            Do While ii < jj 'ii<jj表示本轮排序未完成
                '若Flag1放在Xuhao1位置,则先让jj向小变化; _
                若Flag1放在Xuhao2位置,则先让ii向大变化。
                Do While ii < jj And Cells(jj, Lie1) > Cells(Xuhao1, Lie1) 'jj继续向小变化寻找大数群的边界。
                    Cells(1, Lie1) = "向上寻找小数,即<" & Cells(Xuhao1, Lie1) & "的数。"
                    Call CCdengdai(Time1)
                    Call CCxunzhao(jj, -1)
                    jj = jj - 1
                    If jj = ii Then
                        Cells(ii, Lie1).Interior.Color = RGB(0, 255, 255)
                        Call CCdengdai(Time1)
                    End If
                Loop
                Do While ii < jj And Cells(ii, Lie1) <= Cells(Xuhao1, Lie1) 'ii继续向大变化寻找小数群的边界。
                    Cells(1, Lie1) = "向下寻找大数,即≥" & Cells(Xuhao1, Lie1) & "的数。"
                    Call CCdengdai(Time1)
                    Call CCxunzhao(ii, 1)
                    ii = ii + 1
                    If ii > Xuhao1 Then
                        Cells(ii, Lie1).Interior.Color = RGB(0, 0, 255)
                        Cells(Xuhao1, Lie1).Interior.Color = RGB(255, 0, 0)
                    End If
                    If ii = jj Then
                        Cells(ii, Lie1).Interior.Color = RGB(0, 255, 255)
                    End If
                    Call CCdengdai(Time1)
                Loop
                If ii = jj Then 'ii=jj表示ii和jj现在的位置就是小数群和大数群的交界位置。
                    Cells(1, Lie1) = "将中数" & Cells(Xuhao1, Lie1) & "换到大数和小数交界位置。"
                    Call CCdengdai(Time1)
                    Call CCjiaohuan(ii, Xuhao1) '接着将Flag1放到小数和大数相交的ii位置。
                    Cells(ii, Lie1).Interior.Color = RGB(122, 122, 122)
                    Exit Do
                Else 'ii<jj表示此时,Arr1(ii),Arr1(jj)不满足前小后大关系,小数群和大数群有交叉。
                    Cells(1, Lie1) = "将小数换到上面,大数换到下面。"
                    Call CCdengdai(Time1)
                    Call CCjiaohuan(ii, jj) '交换Arr1(ii),Arr1(jj)这两个元素。
                End If
            Loop
            If ii > Xuhao1 Then
                Cells(1, Lie1) = "对" & Cells(Xuhao1, Lie1) & "到" & Cells(ii - 1, Lie1) & "之间的数排序。"
                Call CCdengdai(Time1)
                Call Quicksort(Xuhao1, ii - 1) '对小数群进行排序
            End If
            If ii < Xuhao2 Then
            Cells(1, Lie1) = "对" & Cells(ii + 1, Lie1) & "到" & Cells(Xuhao2, Lie1) & "之间的数排序。"
            Call CCdengdai(Time1)
            Call Quicksort(ii + 1, Xuhao2) '对大数群进行排序
            End If
        End If
        Range(Cells(Xuhao1, Lie1), Cells(Xuhao2, Lie1)).Interior.Color = RGB(122, 122, 122)
        Call CCdengdai(Time1)
    End If
    Range(Cells(Xuhao1, Lie1), Cells(Xuhao2, Lie1)).Interior.Color = RGB(122, 122, 122)
    Call CCdengdai(Time1)
End Sub
Private Sub CCjiaohuan(Row1&, Row2&)
    Dim Row3&, Row4&, Row5&
    If Row1 <> Row2 Then
        If Row1 < Row2 Then
            Row3 = Row1
            Row4 = Row2
        Else
            Row3 = Row2
            Row4 = Row1
        End If
        Call CCyidong(Row3, 0, Lie1, 1)
        If Row3 = Row4 - 1 Then
           Call CCyidong(Row4, -1, Lie1, 0)
        Else
            Call CCyidong(Row4, 0, Lie1, -1)
            Row5 = Row4 - 1
            Call CCdengdai(Time1)
            Call CCyidong(Row4, Row3 - Row4, Lie1 - 1, 0)
            Call CCyidong(Row3, 0, Lie1 - 1, 1)
        End If
        Row5 = Row3 + 1
        Call CCdengdai(Time1)
        Call CCyidong(Row3, Row4 - Row3, Lie1 + 1, 0)
        Call CCyidong(Row4, 0, Lie1 + 1, -1)
    End If
End Sub
Private Sub CCyidong(Row1&, Num1&, Col1&, Num2&)
    If Len(Cells(Row1, Col1)) > 0 Then
        Cells(Row1 + Num1, Col1 + Num2) = Cells(Row1, Col1)
        Cells(Row1, Col1) = ""
    End If
    'Cells(Row1 + Num1, Col1 + Num2).Interior.Color = Cells(Row1, Col1).Interior.Color
    'Cells(Row1, Col1).Interior.Color = RGB(255, 255, 255)
    Cells(Row1 + Num1, Col1 + Num2 - Cha1).Interior.Color = Cells(Row1, Col1 - Cha1).Interior.Color
    Cells(Row1, Col1 - Cha1).Interior.Color = RGB(255, 255, 255)
    Call CCdengdai(Time1)
End Sub
Private Sub CCxunzhao(Row1&, Num1&)
    Cells(Row1 + Num1, Lie1).Interior.Color = Cells(Row1, Lie1).Interior.Color
    Cells(Row1, Lie1).Interior.Color = RGB(255, 255, 255)
    Call CCdengdai(Time1)
End Sub
Private Sub CCdengdai(ds1#)
    Dim sTimer As Date
    sTimer = Timer
    Do While Format((Timer - sTimer), "0.00") < ds1
        DoEvents
    Loop
End Sub

快速排序法演示地址

https://v.youku.com/v_show/id_XNTgwNDA5OTIwMA==.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

ggggwhw

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值