;; 
;;=====================================================================================----- 
;; 
;;FUNCTION       QuickSort() 
;; 
;;ACTION         Sort an array 
;; 
;;AUTHOR         BrianTX  
;; 
;;CONTRIBUTORS   Christophe Melin 
;; 
;;VERSION        1.1 - 2004/09/10 
;; 
;;HISTORY        1.0 - 2002/09/30 - Initial Release 
;;               1.1 - 2004/09/10 - Add the ability to sort an array of array 
;;                                  and rename variables for better understanding. 
;; 
;;SYNTAX         QuickSort(Array, [IndexCol]) 
;; 
;;PARAMETERS     Array - REQUIRED - Array 
;;               - The array to sort 
;; 
;;               IndexCol - OPTIONAL - Integer 
;;               - The number of the column to sort on 
;; 
;;REMARKS         
;; 
;;RETURNS        Sorted array 
;; 
;;DEPENDENCIES   QuickSortItem() (in this file) 
;; 
;;TESTED WITH    W2K3, W2K8, W2K12 
;; 
;;EXAMPLES       $aSorted = QuickSort($aUnsorted) 
; 
----------------------------------------------------------------------------- 
Function QuickSort($a, OPTIONAL $IndexCol)
 
  Dim $StackPointer				; stack pointer  
  Dim $LowerIndex				; lower index  
  Dim $UpperIndex				; upper index  
  Dim $Pivot					; value of pivot  
  Dim $TempSwappingValue			; temp variable for swapping elements  
  Dim $Index					; stores either lower or upper index of unsorted segment of the array  
  Dim $I					; counter moving from lower index to the right  
  Dim $J					; counter moving from upper index to the left  
  Dim $LowerItem				; value to compare with  
  Dim $StackSize, $StackIncr			;  
  Dim $ExitLoop					;  
 
  $StackSize = 8
  $StackIncr = $StackSize
 
  Dim $LowerIndexStack[$StackSize]		; lower index stack  
  Dim $UpperIndexStack[$StackSize]		; upper index stack  
 
 
  If $Indexcol
    $Indexcol = CStr($Indexcol)
    If $Indexcol < 0
      $Indexcol = 0
    EndIf
  else
    $Indexcol = 0
  EndIf
 
  $LowerIndexStack[0] = 0
  $UpperIndexStack[0] = UBOUND($a)
  $StackPointer = 0
 
  While $StackPointer >= 0
    $LowerIndex = $LowerIndexStack[$StackPointer]
    $UpperIndex = $UpperIndexStack[$StackPointer]
 
    While $LowerIndex < $UpperIndex
      $Pivot = $LowerIndex + ($UpperIndex - $LowerIndex) / 2
      $TempSwappingValue = $a[$LowerIndex]
      $A[$LowerIndex] = $A[$Pivot]
      $A[$Pivot] = $TempSwappingValue
      $I = $LowerIndex + 1
      $J = $UpperIndex
      $ExitLoop = 0
 
      Do
        $LowerItem = QuickSortItem($A[$LowerIndex], $Indexcol)
        While ($I < $J) And (QuickSortItem($A[$I], $Indexcol) < $LowerItem)
          $I = $I + 1
        Loop
        While ($J> = $I) And ($LowerItem < QuickSortItem($A[$J], $Indexcol))
          $J = $J - 1
        Loop
        If $I> = $J
          $ExitLoop = 1
        Else
          $TempSwappingValue=$A[$I]
          $A[$I] = $A[$J]
          $A[$J] = $TempSwappingValue
          $J = $J - 1
          $I = $I + 1
        EndIf
      Until $ExitLoop = 1
 
      $TempSwappingValue = $a[$LowerIndex]
      $A[$LowerIndex] = $a[$J]
      $A[$J] = $TempSwappingValue
      $Index = $J
      If $Index - $LowerIndex <= $UpperIndex - $Index
        If $Index+1 < $UpperIndex
          If $StackPointer > $StackSize
            $StackSize = $StackSize + $StackIncr
            Redim Preserve $LowerIndexStack[$StackSize]
            Redim Preserve $UpperIndexStack[$StackSize]
          EndIf
 
          $LowerIndexStack[$StackPointer] = $Index+1
          $UpperIndexStack[$StackPointer] = $UpperIndex
          $StackPointer = $StackPointer + 1
        EndIf
        $UpperIndex = $Index-1
      Else
        If $Index-1 > $LowerIndex
          If $StackPointer > $StackSize
            $StackSize = $StackSize + $StackIncr
            Redim Preserve $LowerIndexStack[$StackSize]
            Redim Preserve $UpperIndexStack[$StackSize]
          EndIf
 
          $LowerIndexStack[$StackPointer]=$LowerIndex
          $UpperIndexStack[$StackPointer]=$Index-1
          $StackPointer = $StackPointer + 1
        EndIf
        $LowerIndex = $Index + 1
      EndIf
    Loop
    $StackPointer = $StackPointer - 1
  Loop
 
  $QuickSort=$A
 
  Exit 0
 
EndFunction
 
 
 
Function QuickSortItem($Value, $Index)
 
  If VarType($Value) & 8192
    If ($Index <= UBound($Value))
      $QuickSortItem = $Value[$Index]
    Else
      $QuickSortItem = ''
    EndIf
  Else
    $QuickSortItem = $Value
  EndIf
 
  Exit 0
 
EndFunction