YoushouldhavereceivedacopyoftheGNUGeneralPublicLicense alongwiththisprogram;ifnot,writetotheFreeSoftware
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335 USA */
/* We need to use qsort with 2 different compare functions */ #ifdef QSORT_EXTRA_CMP_ARGUMENT #define CMP(A,B) ((*cmp)(cmp_argument,(A),(B))) #else #define CMP(A,B) ((*cmp)((A),(B))) #endif
#ifdef QSORT_EXTRA_CMP_ARGUMENT
qsort_t my_qsort2(void *base_ptr, size_t count, size_t size, qsort_cmp2 cmp, void *cmp_argument) #else
qsort_t my_qsort(void *base_ptr, size_t count, size_t size, qsort_cmp cmp) #endif
{ char *low, *high, *pivot;
stack_node stack[STACK_SIZE], *stack_ptr;
my_bool ptr_cmp; /* Handle the simple case first */ /* This will also make the rest of the code simpler */ if (count <= 1)
SORT_RETURN;
low = (char*) base_ptr;
high = low+ size * (count - 1);
stack_ptr = stack + 1; #ifdef HAVE_valgrind /* The first element in the stack will be accessed for the last POP */
stack[0].low=stack[0].high=0; #endif
pivot = (char *) my_alloca((int) size);
ptr_cmp= size == sizeof(char*) && (intptr_t)low % sizeof(char*) == 0;
/* The following loop sorts elements between high and low */ do
{ char *low_ptr, *high_ptr, *mid;
count=((size_t) (high - low) / size)+1; /* If count is small, then an insert sort is faster than qsort */ if (count < THRESHOLD_FOR_INSERT_SORT)
{ for (low_ptr = low + size; low_ptr <= high; low_ptr += size)
{ char *ptr; for (ptr = low_ptr; ptr > low && CMP(ptr - size, ptr) > 0;
ptr -= size)
SWAP(ptr, ptr - size, size, ptr_cmp);
}
POP(low, high); continue;
}
/* Try to find a good middle element */
mid= low + size * (count >> 1); if (count > 40) /* Must be bigger than 24 */
{
size_t step = size* (count / 8);
MEDIAN(low, low + step, low+step*2);
MEDIAN(mid - step, mid, mid+step);
MEDIAN(high - 2 * step, high-step, high); /* Put best median in 'mid' */
MEDIAN(low+step, mid, high-step);
low_ptr = low;
high_ptr = high;
} else
{
MEDIAN(low, mid, high); /* The low and high argument are already in sorted against 'pivot' */
low_ptr = low + size;
high_ptr = high - size;
}
memcpy(pivot, mid, size);
do
{ while (CMP(low_ptr, pivot) < 0)
low_ptr += size; while (CMP(pivot, high_ptr) < 0)
high_ptr -= size;
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.