Vous êtes sur la page 1sur 17

frmSort.

frm

Option Explicit Private Enum SortType stNone = 0 stBubble = 1 stSelection = 2 stInsertion = 3 stQuick = 4 stMerge = 5 stHeap = 6 stComb = 7 stShell = 8 stShaker = 9 stRadix = 10 End Enum Private Declare Sub Sleep Lib "kernel32" (ByVal dwMilliseconds As Long) Dim bStop As Boolean Private Sub cmdStart_Click() Dim cSort(3) As cVisualSorting Dim eChoice(3) As SortType Dim bDone(3) As Boolean Dim lVals(100) As Long Dim i As Long Dim rA As Long Dim rB As Long Dim iTmp As Long cmdStart.Enabled = False 'Generate numbers

For i = 0 To 100 lVals(i) = Rand(1, 100) Next i 'Randomize ' For i = 0 To 10 ' rA = Int(Rnd * 11) ' rB = Int(Rnd * 11) ' ' iTmp = lVals(rA) ' lVals(rA) = lVals(rB) ' lVals(rB) = iTmp ' Next i 'Setup the sorting classes For i = 0 To 3 If cboSort(i).Text <> "[None]" Then Set cSort(i) = New cVisualSorting Select Case cboSort(i).Text Case "[None]" eChoice(i) = stNone bDone(i) = True Case "Bubble" eChoice(i) = stBubble cSort(i).StartBubbleSort lVals, picMain(i) Case "Selection" eChoice(i) = stSelection cSort(i).StartSelectionSort lVals, picMain(i) Case "Insertion" eChoice(i) = stInsertion cSort(i).StartInsertionSort lVals, picMain(i) Case "Quick" eChoice(i) = stQuick cSort(i).StartQuickSort lVals, picMain(i) Case "Merge" eChoice(i) = stMerge cSort(i).StartMergeSort lVals, picMain(i) Case "Heap" eChoice(i) = stHeap cSort(i).StartHeapSort lVals, picMain(i) Case "Comb" eChoice(i) = stComb cSort(i).StartCombSort lVals, picMain(i) Case "Shell" eChoice(i) = stShell cSort(i).StartShellSort lVals, picMain(i) Case "Shaker" eChoice(i) = stShaker cSort(i).StartShakerSort lVals, picMain(i) Case "Radix" eChoice(i) = stRadix cSort(i).StartRadixSort lVals, picMain(i)

End Select Next i 'Perform the sorts bStop = False Do Until (bDone(0) And bDone(1) And bDone(2) And bDone(3)) Or bStop For i = 0 To 3 If Not bDone(i) Then Select Case eChoice(i) Case stBubble bDone(i) = (cSort(i).BubbleSort = 1) Case stSelection bDone(i) = (cSort(i).SelectionSort = 1) Case stInsertion bDone(i) = (cSort(i).InsertionSort = 1) Case stQuick bDone(i) = (cSort(i).QuickSort = 1) Case stMerge bDone(i) = (cSort(i).MergeSort = 1) Case stHeap bDone(i) = (cSort(i).HeapSort = 1) Case stComb bDone(i) = (cSort(i).CombSort = 1) Case stShell bDone(i) = (cSort(i).ShellSort = 1) Case stShaker bDone(i) = (cSort(i).ShakerSort = 1) Case stRadix bDone(i) = (cSort(i).RadixSort = 1) End Select End If Next i Sleep 5 DoEvents Loop cmdStart.Enabled = True End Sub Private Sub cmdStop_Click() bStop = True End Sub Private Sub Form_Load() Randomize cboSort(0).ListIndex = 0 cboSort(1).ListIndex = 0 cboSort(2).ListIndex = 0 cboSort(3).ListIndex = 0 End Sub Private Sub Form_QueryUnload(Cancel As Integer, UnloadMode As Integer) cmdStop_Click

End Sub Public Function Rand(ByVal Low As Long, _ ByVal High As Long) As Long Rand = Int((High - Low + 1) * Rnd) + Low End Function

cVisualSorting.cls Option Explicit Private Type QuickSortStack iLeftEnd As Long iRightEnd As Long End Type 'Generic Dim iOuter As Long Dim iInner As Long Dim iLBound As Long Dim iUBound As Long Dim iTemp As Long Dim iFinished As Long Dim iMax As Long Dim iMin As Long Dim lngArray() As Long Dim arrTemp() As Long 'Quicksort Dim qsStack() As QuickSortStack Dim iStackPtr As Long Dim iLeftCur As Long Dim iRightCur As Long Dim iLeftEnd As Long Dim iRightEnd As Long Dim iPivot As Long Dim iState As Long 'Merge Sort Dim iSegSize As Long Dim iSegNext As Long Dim iFirst As Long Dim iSecond As Long Dim iResult As Long Dim iPassState As Long Dim iMergeState As Long Dim iStartFirst As Long Dim iEndFirst As Long Dim iEndSecond As Long 'Heap sort Dim iArrSize As Long Dim iRoot As Long Dim iChild As Long Dim iElement As Long Dim iCurrent As Long 'Comb and shell

Dim iSpacing As Long 'Shaker Dim iLower As Long Dim iUpper As Long 'Radix Dim iSorts As Long Dim iLoop As Long Dim arrCounts(255) As Long Dim arrOffsets(255) As Long Dim iBucket As Long Dim picOutput As PictureBox Dim picTempout As PictureBox Private Sub UpdateDisplay(ByVal iRed As Long, ByVal iBlue As Long, Optional ByVal iGreen As Long = -1, Optional ByVal useTemp As Long) Dim i As Long iRed = iRed * 2 iBlue = iBlue * 2 With picOutput .Cls picOutput.Line (0, iRed)-(.ScaleWidth, iRed), vbRed picOutput.Line (0, iBlue)-(.ScaleWidth, iBlue), vbBlue If iGreen > -1 Then picOutput.Line (0, iGreen * 2)-(.ScaleWidth, iGreen * 2), vbGreen If useTemp Then For i = iLBound To iUBound picOutput.Line (0, i * 2)-(arrTemp(i), i * 2) Next i Else For i = iLBound To iUBound picOutput.Line (0, i * 2)-(lngArray(i), i * 2) Next i End If .Refresh End With DoEvents End Sub Public Sub StartBubbleSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) iOuter = iLBound iInner = iLBound End Sub

Public Function BubbleSort() As Long iInner = iInner + 1 If iInner = iUBound - iOuter Then iOuter = iOuter + 1 If iOuter = iUBound Then BubbleSort = 1 Exit Function Else iInner = iLBound End If End If If lngArray(iInner) > lngArray(iInner + 1) Then iTemp = lngArray(iInner) lngArray(iInner) = lngArray(iInner + 1) lngArray(iInner + 1) = iTemp End If UpdateDisplay iInner, iUBound - iOuter End Function Public Sub StartSelectionSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) iOuter = iUBound iInner = iLBound iMax = iLBound End Sub Public Function SelectionSort() As Long iInner = iInner + 1 If iInner > iOuter Then iTemp = lngArray(iMax) lngArray(iMax) = lngArray(iOuter) lngArray(iOuter) = iTemp iOuter = iOuter - 1 If iOuter = iLBound Then SelectionSort = 1 Else iInner = iLBound iMax = iLBound End If Else If lngArray(iInner) > lngArray(iMax) Then iMax = iInner End If End If

UpdateDisplay iInner, iOuter End Function Public Sub StartInsertionSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) iOuter = iLBound + 1 iInner = iOuter iTemp = lngArray(iOuter) End Sub Public Function InsertionSort() As Long iInner = iInner - 1 If iInner < iLBound Then lngArray(iInner + 1) = iTemp iOuter = iOuter + 1 If iOuter > iUBound Then InsertionSort = 1 iOuter = iUBound Else iTemp = lngArray(iOuter) End If iInner = iOuter ElseIf lngArray(iInner) <= iTemp Then lngArray(iInner + 1) = iTemp iOuter = iOuter + 1 If iOuter > iUBound Then InsertionSort = 1 iOuter = iUBound Else iTemp = lngArray(iOuter) End If iInner = iOuter Else lngArray(iInner + 1) = lngArray(iInner) End If UpdateDisplay iInner, iOuter End Function Private Sub QSPush(ByVal iLeft As Long, ByVal iRight As Long) If iLeft < iRight Then qsStack(iStackPtr).iLeftEnd = iLeft qsStack(iStackPtr).iRightEnd = iRight

iStackPtr = iStackPtr + 1 End If End Sub Private Function QSPop(ByRef iLeft As Long, ByRef iRight As Long) As Long If iStackPtr Then iStackPtr = iStackPtr - 1 iLeft = qsStack(iStackPtr).iLeftEnd iRight = qsStack(iStackPtr).iRightEnd QSPop = 1 Else QSPop = 0 End If End Function Public Sub StartQuickSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) iStackPtr = 0 iMax = iLBound For iOuter = iLBound To iUBound If lngArray(iOuter) > lngArray(iMax) Then iMax = iOuter Next iOuter iTemp = lngArray(iMax) lngArray(iMax) = lngArray(iUBound) lngArray(iUBound) = iTemp ReDim qsStack((iUBound - iLBound)) QSPush iLBound, iUBound iState = 4 End Sub Public Function QuickSort() As Long Select Case iState Case 0 'Find >= value on left iLeftCur = iLeftCur + 1 If lngArray(iLeftCur) >= iPivot Then iState = 1 Case 1 'Find <= value on right iRightCur = iRightCur - 1 If lngArray(iRightCur) <= iPivot Then iState = 2 Case 2 'Swapping etc If iLeftCur >= iRightCur Then iState = 3

Else iTemp = lngArray(iLeftCur) lngArray(iLeftCur) = lngArray(iRightCur) lngArray(iRightCur) = iTemp iState = 0 End If Case 3 'Recursive part lngArray(iLeftEnd) = lngArray(iRightCur) lngArray(iRightCur) = iPivot QSPush iRightCur + 1, iRightEnd QSPush iLeftEnd, iRightCur - 1 iState = 4 Case 4 'Popping If QSPop(iLeftEnd, iRightEnd) Then iLeftCur = 0 iLeftCur = iLeftEnd iRightCur = iRightEnd + 1 iPivot = lngArray(iLeftEnd) iState = 0 Else QuickSort = 1 End If End Select UpdateDisplay iLeftCur, iLeftEnd, iRightEnd End Function Public Sub StartMergeSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) ReDim arrTemp(iLBound To iUBound) iSegSize = 1 iState = 6 End Sub Private Sub InnerMerge(ByVal iSF As Long, ByVal iEF As Long, ByVal iES As Long) iStartFirst = iSF iEndFirst = iEF iEndSecond = iES iFirst = iStartFirst iSecond = iEndFirst + 1 iResult = iStartFirst iPassState = iState iState = 0

End Sub Private Sub InnerMergePass() iMergeState = iState iSegNext = iLBound iState = 3 End Sub Public Function MergeSort() As Long Dim i As Long Select Case iState Case 0 If iFirst > iEndFirst Then iOuter = iSecond - 1 iState = 1 ElseIf iSecond > iEndSecond Then iOuter = iFirst - 1 iState = 2 Else If lngArray(iFirst) <= lngArray(iSecond) Then arrTemp(iResult) = lngArray(iFirst) iFirst = iFirst + 1 Else arrTemp(iResult) = lngArray(iSecond) iSecond = iSecond + 1 End If iResult = iResult + 1 End If Case 1 iOuter = iOuter + 1 If iOuter > iEndSecond Then iState = iPassState Else arrTemp(iResult) = lngArray(iOuter) iResult = iResult + 1 End If Case 2 iOuter = iOuter + 1 If iOuter > iEndFirst Then iState = iPassState Else arrTemp(iResult) = lngArray(iOuter) iResult = iResult + 1 End If Case 3 If iSegNext <= iUBound - (2 * iSegSize) Then InnerMerge iSegNext, iSegNext + iSegSize - 1, iSegNext + iSegSize + iSegSize - 1 iSegNext = iSegNext + iSegSize + iSegSize

Else iState = 4 End If Case 4 If iSegNext + iSegSize < iUBound Then iState = iMergeState InnerMerge iSegNext, iSegNext + iSegSize - 1, iUBound Else iState = 5 iSegNext = iSegNext - 1 End If Case 5 iSegNext = iSegNext + 1 If iSegNext > iUBound Then iState = iMergeState Else arrTemp(iSegNext) = lngArray(iSegNext) End If Case 6 If iSegSize < iUBound - iLBound Then iState = 7 InnerMergePass Else MergeSort = 1 End If Case 7 iSegSize = iSegSize + iSegSize iState = 8 lngArray = arrTemp InnerMergePass Case 8 iSegSize = iSegSize + iSegSize iState = 6 lngArray = arrTemp End Select UpdateDisplay iResult, iStartFirst, iEndSecond, 1 End Function Public Sub StartHeapSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) iArrSize = iUBound - iLBound

ReDim arrTemp(iLBound To iUBound) iRoot = iArrSize \ 2 iElement = lngArray(iRoot + iLBound) iChild = iRoot + iRoot iState = 0 End Sub Public Function HeapSort() As Long Select Case iState Case 0 If iChild < iArrSize Then If lngArray(iChild + iLBound) < lngArray(iChild + iLBound + 1) Then iChild = iChild + 1 End If End If If iElement >= lngArray(iChild + iLBound) Then iState = 1 Else lngArray((iChild \ 2) + iLBound) = lngArray(iChild + iLBound) iChild = iChild + iChild If iChild >= iArrSize Then iState = 1 End If Case 1 lngArray((iChild \ 2) + iLBound) = iElement iRoot = iRoot - 1 If iRoot = -1 Then iState = 2 iRoot = iUBound arrTemp(iRoot) = lngArray(iLBound) iElement = lngArray(iArrSize + iLBound) iArrSize = iArrSize - 1 iCurrent = 0 iChild = 1 Else iElement = lngArray(iRoot + iLBound) iChild = iRoot + iRoot iState = 0 End If Case 2 If iChild < iArrSize Then If lngArray(iChild + iLBound) < lngArray(iChild + iLBound + 1) Then iChild = iChild + 1 End If

End If If iElement >= lngArray(iChild + iLBound) Then iState = 3 Else lngArray(iCurrent + iLBound) = lngArray(iChild + iLBound) iCurrent = iChild iChild = iChild + iChild If iChild > iArrSize Then iState = 3 End If Case 3 lngArray(iCurrent + iLBound) = iElement iRoot = iRoot - 1 If iRoot = iLBound Then HeapSort = 1 Else arrTemp(iRoot) = lngArray(iLBound) iElement = lngArray(iArrSize + iLBound) iArrSize = iArrSize - 1 iCurrent = 0 iChild = 1 iState = 2 End If End Select If iState < 2 Then UpdateDisplay iChild, iRoot Else UpdateDisplay iChild, iRoot, , 1 End If End Function Public Sub StartCombSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) iOuter = iLBound iSpacing = iUBound - iLBound If iSpacing > 1 Then iSpacing = Int(iSpacing / 1.3) If iSpacing = 0 Then iSpacing = 1 ElseIf iSpacing > 8 And iSpacing < 11 Then iSpacing = 11 End If End If

iFinished = 0 End Sub Public Function CombSort() As Long iOuter = iOuter + 1 If iOuter <= iUBound - iSpacing Then iInner = iOuter + iSpacing If lngArray(iOuter) > lngArray(iInner) Then iTemp = lngArray(iOuter) lngArray(iOuter) = lngArray(iInner) lngArray(iInner) = iTemp iFinished = 0 End If Else If iFinished Then CombSort = 1 Else If iSpacing > 1 Then iSpacing = Int(iSpacing / 1.3) If iSpacing = 0 Then iSpacing = 1 ElseIf iSpacing > 8 And iSpacing < 11 Then iSpacing = 11 End If End If If iSpacing = 1 Then iFinished = 1 iOuter = iLBound - 1 End If End If UpdateDisplay iInner, iOuter End Function Public Sub StartShellSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) iArrSize = (iUBound - iLBound) + 1 iSpacing = 1 If iArrSize > 13 Then Do While iSpacing < iArrSize iSpacing = (3 * iSpacing) + 1 Loop iSpacing = iSpacing \ 9

End If iOuter = iLBound + iSpacing iInner = iOuter iTemp = lngArray(iOuter) End Sub Private Function NextOuterShell() As Long lngArray(iInner + iSpacing) = iTemp iOuter = iOuter + 1 If iOuter > iUBound Then iSpacing = iSpacing \ 3 If iSpacing Then iOuter = iLBound + iSpacing iTemp = lngArray(iOuter) iInner = iOuter Else NextOuterShell = 1 End If Else iInner = iOuter iTemp = lngArray(iOuter) End If End Function Public Function ShellSort() As Long iInner = iInner - iSpacing If iInner >= iLBound Then If lngArray(iInner) <= iTemp Then ShellSort = NextOuterShell Else lngArray(iInner + iSpacing) = lngArray(iInner) End If Else ShellSort = NextOuterShell End If UpdateDisplay iInner, iOuter End Function Public Sub StartShakerSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) iLower = iLBound iUpper = iUBound iInner = iLower - 1 End Sub

Public Function ShakerSort() iInner = iInner + 1 If iInner > iUpper Then iTemp = lngArray(iMax) lngArray(iMax) = lngArray(iUpper) lngArray(iUpper) = iTemp iTemp = lngArray(iMin) lngArray(iMin) = lngArray(iLower) lngArray(iLower) = iTemp If iLower < iUpper Then iLower = iLower + 1 iUpper = iUpper - 1 iMax = iLower iMin = iLower iInner = iLower - 1 Else ShakerSort = 1 End If Else If lngArray(iInner) > lngArray(iMax) Then iMax = iInner ElseIf lngArray(iInner) < lngArray(iMin) Then iMin = iInner End If End If UpdateDisplay iInner, iUpper, iLower End Function Public Sub StartRadixSort(ByRef theArray() As Long, ByRef thePic As PictureBox) Set picOutput = thePic lngArray = theArray iLBound = LBound(lngArray) iUBound = UBound(lngArray) ReDim arrTemp(iLBound To iUBound) iMax = &H80000000 For iLoop = iLBound To iUBound If lngArray(iLoop) > iMax Then iMax = lngArray(iLoop) Next iLoop Do While iMax iSorts = iSorts + 1 iMax = iMax \ 256 Loop iMax = 1 iLoop = 1 iInner = iLBound - 1

iState = 1 End Sub Public Function RadixSort() As Long Select Case iState Case 0 lngArray = arrTemp iMax = iMax * 256 iLoop = iLoop + 1 If iLoop > iSorts Then RadixSort = 1 Else iState = 1 iInner = iLBound - 1 End If Case 1 iInner = iInner + 1 If iInner > iUBound Then iInner = 0 iState = 2 Else iBucket = (lngArray(iInner) \ iMax) And 255 arrCounts(iBucket) = arrCounts(iBucket) + 1 End If Case 2 iInner = iInner + 1 If iInner > 255 Then iInner = iLBound - 1 iState = 3 Else arrOffsets(iInner) = arrOffsets(iInner - 1) + arrCounts(iInner - 1) + iLBound End If Case 3 iInner = iInner + 1 If iInner > iUBound Then iState = 0 Else iBucket = (lngArray(iInner) \ iMax) And 255 arrTemp(arrOffsets(iBucket)) = lngArray(iInner) arrOffsets(iBucket) = arrOffsets(iBucket) + 1 End If End Select UpdateDisplay iInner, 0, , 1 End Function

Vous aimerez peut-être aussi