/* The function initFromPartnStack initializes an existing R-priority queue tothepointsinagivencellofthetoppartitiononagivenpartition
stack. */
void initFromPartnStack(
RPriorityQueue *rpq, /* R-priority queue to initialize. */
PartitionStack *PiStack, /* The partition stack. */ Unsigned cellNumber, /* The R-priority queue is initialized to cell
cellNumber of top partition on bfPiStack */ const RBase *const AAA) /* Only omega and invOmega are needed. */
{ Unsigned i, j, p, a, b, k, m, t, left, right, mid, splitKey, bound, tRank,
splitKeyRank, final;
UnsignedS qSortStack[20][2]; Unsigned qSortTop = 0;
UnsignedS *const omega = AAA->omega, *const invOmega = AAA->invOmega; char *temp;
/* Check that r-priority queue has required size (for debugging). */ /* assert( PiStack->cellSize[cellNumber] == rpq->maxSize); */
/* Copy the appropriate cell of the partition stack to the R-priority
queue. */
i = 0; for ( j = PiStack->startCell[cellNumber] , bound = j +
PiStack->cellSize[cellNumber] ; j < bound ; ++j )
rpq->pointList[++i] = PiStack->pointList[j];
rpq->size = i;
/* Sort the R-priority queue in descending order. The following strategyisused:Ifthesizeis<=10,straightinsertionsort isused.Otherwise,ifthesizeis>=degree/10,anarrayofflags isused.Otherwise,quicksortisused,withsublistsofsize<=10
being handled by straight insertion sort. */
/* If the size is <= 10, sort directly by straight insertion sort and
return. */ if ( rpq->size <= 10 ) {
rpq->pointList[0] = 0;
invOmega[0] = rpq->degree+1; for ( m = 2 ; m <= rpq->size ; ++m) {
t = rpq->pointList[m];
tRank = invOmega[t];
k = m - 1; while ( invOmega[rpq->pointList[k]] < tRank ) {
rpq->pointList[k+1] = rpq->pointList[k];
--k;
}
rpq->pointList[k+1] = t;
} return;
}
/* Otherwise, if the size is at least 1/10 the degree, we sort using an
index into a Boolean array. */ if ( rpq->size >= rpq->degree / 10 ) {
temp = allocBooleanArrayDegree(); for ( m = 1 ; m <= rpq->degree ; ++m )
temp[m] = FALSE; for ( m = 1 ; m <= rpq->size ; ++m )
temp[invOmega[rpq->pointList[m]]] = TRUE;
p = 1; for ( m = rpq->degree ; m >= 1 ; --m ) if ( temp[m] )
rpq->pointList[p++] = omega[m];
freeBooleanArrayDegree( temp); return;
}
/* In the remaining case, we partially sort using quicksort. Sublists ofsize<=qSortCutOffareleftunsorted.Afinalpasswithstraight
insertion sort completes the sort. */
rpq->pointList[0] = 0;
invOmega[0] = rpq->degree+1; if ( rpq->size > qSortCutOff ) {
rpq->pointList[rpq->size+1] = rpq->degree + 1;
invOmega[rpq->degree+1] = 0;
RPQ_PUSH( 1, rpq->size);
} while ( qSortTop >= 1 ) {
RPQ_POP( a, b); while ( b - a >= qSortCutOff ) {
left = a; right = b + 1; mid = (a + b) / 2;
splitKey = rpq->pointList[mid];
splitKeyRank = invOmega[splitKey];
EXCHANGE( rpq->pointList[left], rpq->pointList[mid], t) do { while ( invOmega[rpq->pointList[++left]] > splitKeyRank )
; while ( invOmega[rpq->pointList[--right]] < splitKeyRank )
; if ( left < right )
EXCHANGE( rpq->pointList[left], rpq->pointList[right], t)
} while ( left < right );
final = right;
EXCHANGE( rpq->pointList[a], rpq->pointList[final], t) if ( final - a >= b - final ) if ( b - final >= qSortCutOff ) {
RPQ_PUSH( a, final-1);
a = final + 1;
} else
b = final - 1; else if ( final - a >= qSortCutOff ) {
RPQ_PUSH( final+1, b);
b = final - 1;
} else
a = final + 1;
}
}
/* Now finish with straight insertion sort. */ for ( m = 2 ; m <= rpq->size ; ++m) {
t = rpq->pointList[m];
tRank = invOmega[t];
k = m - 1; while ( invOmega[rpq->pointList[k]] < tRank ) {
rpq->pointList[k+1] = rpq->pointList[k];
--k;
}
rpq->pointList[k+1] = t;
}
}
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.