// quickSort5.cc -- tail recursion removed, and insertion used for small. // ... and array access tuned for performance. // code by saunders following suggestions made in Sedgewick, chapter 9. 2/96 typedef int itemType; // Must be a type on which the comparator > can be used. // sort, id, and ate will be used by main. void quickSort(itemType* base, itemType* hi); char* id = "quick"; char* ate = "g(N) := N*log[2](N);"; /* dependency chart (indented means used by above): quickSort partition swap insertionSort quickSort */ inline void swap(itemType* i, itemType* j){ itemType v = *i; *i = *j; *j = v; } inline itemType* partition(itemType* base, itemType* hi){ itemType v = *hi; itemType* i = base; itemType* j = hi; for (;;) { while (v > *(++i)); // *base+1.. *i-1 are < v. while (*(--j) > v); // *j+1..*hi are > v. if (i >= j) break; // partition almost done swap(i, j); } swap(i, hi); return i; } inline void insertionSort(itemType* base, itemType* hi); void quickSort(itemType* base, itemType* hi){// hi - base == N. // The items *(base+1) .. *hi are permuted into sorted order. // Side effect: *base is overwritten. top: if (hi > base + 20){ itemType* mid = partition(base, hi); quickSort(base, mid - 1); base = mid; goto top; } } void insertionSort(itemType* base, itemType* hi){ // The items in positions base+1 .. hi are permuted into sorted order. // Side effect: a[0] is overwritten. itemType* i; itemType* j; itemType v; for (i = base+2; i <= hi; i++) { // invariant: *(base+1)..*(i-1) is sorted. v = *i; j = i; itemType temp = *base; *base = v; // sentinel for while loop. while (*(j-1) > v) { *j = *(j-1); j--; } *j = v; *base = temp; } // Now *(base+1)..*(i-1) is sorted and i = hi+1. // Therefore *(base+1)..*hi is sorted. } void sort(itemType a[], int lo, int hi){ quickSort(a+lo-1, a+hi); insertionSort(a+lo-1, a+hi); }