/**CFile**************************************************************** FileName [vecQue.h] SystemName [ABC: Logic synthesis and verification system.] PackageName [Resizable arrays.] Synopsis [Priority queue.] Author [Alan Mishchenko] Affiliation [UC Berkeley] Date [Ver. 1.0. Started - June 20, 2005.] Revision [$Id: vecQue.h,v 1.00 2005/06/20 00:00:00 alanmi Exp $] ***********************************************************************/ #ifndef ABC__misc__vec__Queue_h #define ABC__misc__vec__Queue_h //////////////////////////////////////////////////////////////////////// /// INCLUDES /// //////////////////////////////////////////////////////////////////////// #include ABC_NAMESPACE_HEADER_START //////////////////////////////////////////////////////////////////////// /// PARAMETERS /// //////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////// /// BASIC TYPES /// //////////////////////////////////////////////////////////////////////// typedef struct Vec_Que_t_ Vec_Que_t; struct Vec_Que_t_ { int nCap; int nSize; int * pHeap; int * pOrder; float ** pCostsFlt; // owned by the caller }; static inline float Vec_QuePrio( Vec_Que_t * p, int v ) { return *p->pCostsFlt ? (*p->pCostsFlt)[v] : v; } //////////////////////////////////////////////////////////////////////// /// MACRO DEFINITIONS /// //////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////// /// FUNCTION DEFINITIONS /// //////////////////////////////////////////////////////////////////////// /**Function************************************************************* Synopsis [] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ static inline Vec_Que_t * Vec_QueAlloc( int nCap ) { Vec_Que_t * p; p = ABC_CALLOC( Vec_Que_t, 1 ); if ( nCap < 16 ) nCap = 16; p->nSize = 1; p->nCap = nCap + 1; p->pHeap = ABC_FALLOC( int, p->nCap ); p->pOrder = ABC_FALLOC( int, p->nCap ); return p; } static inline void Vec_QueFree( Vec_Que_t * p ) { ABC_FREE( p->pOrder ); ABC_FREE( p->pHeap ); ABC_FREE( p ); } static inline void Vec_QueFreeP( Vec_Que_t ** p ) { if ( *p ) Vec_QueFree( *p ); *p = NULL; } static inline void Vec_QueSetPriority( Vec_Que_t * p, float ** pCosts ) { assert( p->pCostsFlt == NULL ); p->pCostsFlt = pCosts; } static inline void Vec_QueGrow( Vec_Que_t * p, int nCapMin ) { if ( p->nCap >= nCapMin ) return; p->pHeap = ABC_REALLOC( int, p->pHeap, nCapMin ); p->pOrder = ABC_REALLOC( int, p->pOrder, nCapMin ); memset( p->pHeap + p->nCap, 0xff, (nCapMin - p->nCap) * sizeof(int) ); memset( p->pOrder + p->nCap, 0xff, (nCapMin - p->nCap) * sizeof(int) ); p->nCap = nCapMin; } static inline void Vec_QueClear( Vec_Que_t * p ) { int i; assert( p->pHeap[0] == -1 ); for ( i = 1; i < p->nSize; i++ ) { assert( p->pHeap[i] >= 0 && p->pOrder[p->pHeap[i]] == i ); p->pOrder[p->pHeap[i]] = -1; p->pHeap[i] = -1; } p->nSize = 1; } /**Function************************************************************* Synopsis [] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ static inline int Vec_QueSize( Vec_Que_t * p ) { assert( p->nSize > 0 ); return p->nSize - 1; } static inline int Vec_QueTop( Vec_Que_t * p ) { return Vec_QueSize(p) > 0 ? p->pHeap[1] : -1; } static inline float Vec_QueTopPriority( Vec_Que_t * p ) { return Vec_QueSize(p) > 0 ? Vec_QuePrio(p, p->pHeap[1]) : -ABC_INFINITY; } /**Function************************************************************* Synopsis [] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ static inline int Vec_QueMoveUp( Vec_Que_t * p, int v ) { float Cost = Vec_QuePrio(p, v); int i = p->pOrder[v]; int parent = i >> 1; int fMoved = 0; assert( p->pOrder[v] != -1 ); assert( p->pHeap[i] == v ); while ( i > 1 && Cost > Vec_QuePrio(p, p->pHeap[parent]) ) { p->pHeap[i] = p->pHeap[parent]; p->pOrder[p->pHeap[i]] = i; i = parent; parent = i >> 1; fMoved = 1; } p->pHeap[i] = v; p->pOrder[v] = i; return fMoved; } static inline void Vec_QueMoveDown( Vec_Que_t * p, int v ) { float Cost = Vec_QuePrio(p, v); int i = p->pOrder[v]; int child = i << 1; while ( child < p->nSize ) { if ( child + 1 < p->nSize && Vec_QuePrio(p, p->pHeap[child]) < Vec_QuePrio(p, p->pHeap[child+1]) ) child++; assert( child < p->nSize ); if ( Cost >= Vec_QuePrio(p, p->pHeap[child])) break; p->pHeap[i] = p->pHeap[child]; p->pOrder[p->pHeap[i]] = i; i = child; child = child << 1; } p->pHeap[i] = v; p->pOrder[v] = i; } static inline void Vec_QueUpdate( Vec_Que_t * p, int v ) { if ( !Vec_QueMoveUp( p, v ) ) Vec_QueMoveDown( p, v ); } /**Function************************************************************* Synopsis [] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ static inline int Vec_QueIsMember( Vec_Que_t * p, int v ) { assert( v >= 0 ); return (int)( v < p->nCap && p->pOrder[v] >= 0 ); } static inline void Vec_QuePush( Vec_Que_t * p, int v ) { if ( p->nSize >= p->nCap ) Vec_QueGrow( p, Abc_MaxInt(p->nSize+1, 2*p->nCap) ); if ( v >= p->nCap ) Vec_QueGrow( p, Abc_MaxInt(v+1, 2*p->nCap) ); assert( p->nSize < p->nCap ); assert( p->pOrder[v] == -1 ); assert( p->pHeap[p->nSize] == -1 ); p->pOrder[v] = p->nSize; p->pHeap[p->nSize++] = v; Vec_QueMoveUp( p, v ); } static inline int Vec_QuePop( Vec_Que_t * p ) { int v, Res; assert( p->nSize > 1 ); Res = p->pHeap[1]; p->pOrder[Res] = -1; if ( --p->nSize == 1 ) { p->pHeap[1] = -1; return Res; } v = p->pHeap[p->nSize]; p->pHeap[p->nSize] = -1; p->pHeap[1] = v; p->pOrder[v] = 1; Vec_QueMoveDown( p, v ); return Res; } /**Function************************************************************* Synopsis [] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ static inline void Vec_QuePrint( Vec_Que_t * p ) { int i, k, m; for ( i = k = 1; i < p->nSize; i += k, k *= 2 ) { for ( m = 0; m < k; m++ ) if ( i+m < p->nSize ) printf( "%-5d", p->pHeap[i+m] ); printf( "\n" ); for ( m = 0; m < k; m++ ) if ( i+m < p->nSize ) printf( "%-5.0f", Vec_QuePrio(p, p->pHeap[i+m]) ); printf( "\n" ); printf( "\n" ); } } /**Function************************************************************* Synopsis [] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ static inline void Vec_QueCheck( Vec_Que_t * p ) { int i, child; assert( p->nSize > 0 ); assert( p->nSize <= p->nCap ); // check mapping for ( i = 0; i < p->nSize-1; i++ ) assert( p->pOrder[i] > 0 ); for ( ; i < p->nCap; i++ ) assert( p->pOrder[i] == -1 ); // check heap assert( p->pHeap[0] == -1 ); for ( i = 0; i < p->nSize-1; i++ ) assert( p->pHeap[p->pOrder[i]] == i ); for ( i++; i < p->nCap; i++ ) assert( p->pHeap[i] == -1 ); // check heap property for ( i = 1; i < p->nSize; i++ ) { child = i << 1; if ( child < p->nSize ) assert( Vec_QuePrio(p, p->pHeap[i]) >= Vec_QuePrio(p, p->pHeap[child]) ); child++; if ( child < p->nSize ) assert( Vec_QuePrio(p, p->pHeap[i]) >= Vec_QuePrio(p, p->pHeap[child]) ); } } /**Function************************************************************* Synopsis [] Description [] SideEffects [] SeeAlso [] ***********************************************************************/ static inline void Vec_QueTest( Vec_Flt_t * vCosts ) { Vec_Int_t * vTop; Vec_Que_t * p; int i, Entry; // start the queue p = Vec_QueAlloc( Vec_FltSize(vCosts) ); Vec_QueSetPriority( p, Vec_FltArrayP(vCosts) ); for ( i = 0; i < Vec_FltSize(vCosts); i++ ) Vec_QuePush( p, i ); // Vec_QuePrint( p ); Vec_QueCheck( p ); // find the topmost 10% vTop = Vec_IntAlloc( Vec_FltSize(vCosts) / 10 ); while ( Vec_IntSize(vTop) < Vec_FltSize(vCosts) / 10 ) Vec_IntPush( vTop, Vec_QuePop(p) ); // Vec_IntPrint( vTop ); // Vec_QueCheck( p ); // queque is not ready at this point!!! // put them back Vec_IntForEachEntry( vTop, Entry, i ) Vec_QuePush( p, Entry ); Vec_IntFree( vTop ); Vec_QueCheck( p ); Vec_QueFree( p ); } /* { extern void Vec_QueTest( Vec_Flt_t * p ); Vec_QueTest( p->vTimesOut ); } */ //////////////////////////////////////////////////////////////////////// /// END OF FILE /// //////////////////////////////////////////////////////////////////////// ABC_NAMESPACE_HEADER_END #endif