// Routines to sort arrays of integers. // (c) 1997 duane a. bailey import structure.*; public class QuickSort { public static void main(String args[]) { int n = args.length; int i; int data[] = new int[n]; for (i = 0; i < n; i++) { data[i] = Integer.parseInt(args[i]); } quickSortIterative(data,data.length); for (i = 0; i < n; i++) { System.out.print(data[i]+" "); } System.out.println(); } //+quickSortIterative public static void quickSortIterative(int data[], int n) // pre: n <= data.length // post: data[0..n] in ascending order { Stack callStack = new StackList(); callStack.push(new callFrame(0,n-1)); while (!callStack.isEmpty()) { // some "virtual" method outstanding callFrame curr = (callFrame)callStack.peek(); //-quickSortIterative for (int i = 0; i < callStack.size(); i++) { System.out.print(' '); } System.out.println(curr); //+quickSortIterative if (curr.PC == 1) { // partition and sort lower // return if trivial if (curr.low >= curr.high) { callStack.pop(); continue; } // place the pivot at the correct location curr.pivot = partition(data,curr.low,curr.high); curr.PC++; // sort the smaller values... callStack.push(new callFrame(curr.low,curr.pivot-1)); } else if (curr.PC == 2) { // sort upper curr.PC++; // sort the larger values.... callStack.push(new callFrame(curr.pivot+1,curr.high)); } else { callStack.pop(); continue; } // return } } //-quickSortIterative //+quickSort public static void quickSort(int data[], int n) // post: the values in data[0..n-1] are in ascending order { quickSortRecursive(data,0,n-1); } //-quickSort //+partition private static int partition(int data[], int left, int right) // pre: left <= right // post: data[left] placed in the correct (returned) location { while (true) { // move right "pointer" toward left while (left < right && data[left] < data[right]) right--; if (left < right) swap(data,left++,right); else return left; // move left pointer toward right while (left < right && data[left] < data[right]) left++; if (left < right) swap(data,left,right--); else return right; } } //-partition //+quickSortRecursive private static void quickSortRecursive(int data[], int low, int high) // pre: low <= high // post: data[low..high] in ascending order { int pivot; // the final location of the leftmost value if (low >= high) return; // place the leftmost value at the correct location (pivot) pivot = partition(data,low,high); // 1. Sort the smaller values... quickSortRecursive(data,low,pivot-1); // 2. ...and then sort larger values... quickSortRecursive(data,pivot+1,high); // 3. Done, return! } //-quickSortRecursive public static void quickSort(Vector data,int n) // pre: 0 <= n <= data.size() // post: the values in data[0..n-1] are in ascending order { quickSortRecursive(data,0,n-1); } private static int partition(Vector data, int left, int right) // pre: 0 <= left <= right < data.size() // post: data[left] placed in the correct location { while (true) { // move right "pointer" toward left while (left < right && ((Comparable)data.elementAt(left)) .lessThan((Comparable)data.elementAt(right))) right--; if (left < right) swap(data,left++,right); else return left; // move left pointer toward right while (left < right && ((Comparable)data.elementAt(left)).lessThan((Comparable)data.elementAt(right))) left++; if (left < right) swap(data,left,right--); else return right; } } private static void quickSortRecursive(Vector data, int low, int high) // pre: 0 <= low <= high < data.size() // post: data[low..high] in order { int pivot; if (low >= high) return; // position leftmost value pivot = partition(data,low,high); // sort smaller values quickSortRecursive(data,low,pivot-1); // sort larger values quickSortRecursive(data,pivot+1,high); } //+swap public static void swap(int data[], int i, int j) // pre: 0 <= i,j < data.length // post: data[i] and data[j] are exchanged { int temp; temp = data[i]; data[i] = data[j]; data[j] = temp; } //-swap //+vectorSort public static void swap(Vector data, int i, int j) // pre: 0 <= i,j < data.size() // post: i-th j-th elements of data are exchanged { Object temp; temp = data.elementAt(i); data.setElementAt(data.elementAt(j),i); data.setElementAt(temp,j); } //-vectorSort } //+callFrame class callFrame { int pivot;// location of pivot int low; // left index int high; // right index int PC; // next statment (see #'d comment in recursive code) public callFrame(int l, int h) // post: generate new call frame with low and high as passed { low = l; high = h; PC = 1; } //-callFrame public String toString() { return "<["+low+","+high+"] pivot="+pivot+" PC="+PC+">"; } //+callFrame } //-callFrame