Simple data structures / objects in plain C Snapshot
heap.h
Go to the documentation of this file.
00001 /* Copyright (c) Michael Moser (2011) . 3-clause BSD License applies */
00002 
00003 #ifndef _V_HEAP_H_
00004 #define _V_HEAP_H_
00005 
00006 #ifdef  __cplusplus
00007 extern "C" {
00008 #endif
00009 
00010 #include <cutils/base.h>
00011 
00012 
00013 typedef int (*HEAP_compare) (void *lhs, void *rhs, size_t elmsize);
00014 
00015 /**
00016  * @defgroup HEAP
00017  * @brief Heap data structure; all elements in the heap must be of the same size.
00018  * A heap data structure is an ordered tree where the root node contains the smallest value.
00019  * The smallest element in the whole heap is alway the top element.
00020  * This heap is implemented by an array.
00021  * @{
00022  */
00023 typedef struct  
00024 {
00025         size_t          elmcount;
00026         size_t          elmmaxcount;
00027         size_t          elmsize;
00028 
00029         unsigned char   *buffer;
00030 
00031         HEAP_compare    compare_func;
00032 
00033 }  
00034         HEAP;
00035 
00036 
00037 /* 
00038  * @brief construct a heap object.
00039  * @param ctx (in) allocator interface. (if null we are using the default allocator)
00040  * @param heap (in) the object
00041  * @param elmcount (in) maximum number of elements kept in this heap.
00042  * @param elmsize (in)  size of one element kept in this heap.
00043  * @param grow_at (in) 
00044  * @param compare_func (in) compares two entries in the heap - used to establish heap property.
00045  */
00046 M_INLINE int HEAP_init(  HEAP *heap, size_t elmcount, size_t elmsize, HEAP_compare compare_func)
00047 {
00048         
00049         heap->elmsize = elmsize;
00050         heap->elmcount = 0;
00051         heap->elmmaxcount = elmcount;
00052         heap->compare_func = compare_func;
00053 
00054         heap->buffer = (unsigned char *) malloc( elmcount * elmsize );
00055         if (!heap->buffer) {
00056                 return -1;
00057         }
00058 
00059         return 0;
00060 }
00061 
00062 
00063 
00064 /** 
00065  * @brief free all memory used by the heap (object destructor).
00066  * @heap heap (in) the object.
00067  */
00068 M_INLINE void HEAP_free( HEAP *heap ) 
00069 {
00070         if (heap->buffer) {
00071                 free(heap->buffer);
00072                 heap->buffer = 0;
00073                 heap->elmcount = 0;
00074                 heap->elmmaxcount = 0;
00075                 heap->elmsize = 0;
00076         }
00077 }
00078 
00079 M_INLINE size_t HEAP_size( HEAP *heap)
00080 {
00081         return heap->elmcount;
00082 }
00083 
00084 M_INLINE size_t HEAP_maxsize( HEAP *heap)
00085 {
00086         return heap->elmmaxcount;
00087 }
00088 
00089 M_INLINE size_t HEAP_elmsize( HEAP *heap)
00090 {
00091         return heap->elmsize;
00092 }
00093 
00094 /** 
00095  * @brief returns pointer to the top element of the heap.
00096  * @param heap          (in) the object
00097  * @return pointer to the top element of the heap or 0 if heap is empty.
00098  */
00099 M_INLINE void *HEAP_top( HEAP *heap)
00100 {
00101         if (heap->elmcount == 0) {
00102                 return 0;
00103         }
00104         return heap->buffer;
00105 }
00106 
00107 
00108 M_INLINE void *HEAP_get_at( HEAP *heap, int index)
00109 {
00110         if (heap->elmcount == 0) {
00111                 return 0;
00112         }
00113         if (index > (int) heap->elmcount || index < 0) {
00114                 return 0;
00115         }
00116 
00117         return heap->buffer + index * heap->elmsize;
00118 }
00119 
00120 
00121 /** 
00122  * @brief remove the top element from the heap
00123  * @param heap          (in) the object
00124  */
00125 int HEAP_pop( HEAP *heap);
00126 
00127 /** 
00128  * @brief insert a new element into the heap
00129  * @param heap          (in) the object
00130  * @param element       (in) data of object to be inserted into heap
00131  * @param elmsize       (in) size of data area for element pointer.
00132  */
00133 int HEAP_push( HEAP *heap, void *element, size_t elmsize );
00134 
00135 /** 
00136  * @brief check consistency of heap object.
00137  */
00138 int HEAP_check( HEAP *heap );
00139 
00140 
00141 typedef int  (*HEAP_VISITOR)   (int index, void *elm, size_t elmsize, void *context);
00142 
00143 
00144 
00145 void HEAP_foreach_sorted( HEAP *heap, HEAP_VISITOR eval, void *context);
00146 
00147 
00148 M_INLINE void HEAP_foreach( HEAP *heap, HEAP_VISITOR eval, void *context)
00149 {
00150         size_t i;
00151         size_t sz = heap->elmcount;
00152         size_t elmsz = heap->elmsize;
00153         uint8_t *pos;
00154 
00155         for(pos = heap->buffer, i = 0; i < sz; i++, pos += elmsz) {
00156                 eval( i, pos, elmsz, context ); 
00157         }
00158 }
00159 
00160 M_INLINE int HEAP_findif( HEAP *heap, HEAP_VISITOR eval, void *context, int32_t *retval)
00161 {
00162         size_t i;
00163         size_t sz = heap->elmcount;
00164         size_t elmsz = heap->elmsize;
00165         int32_t ret;
00166         uint8_t *pos;
00167 
00168         if (!retval) {
00169           *retval = 0;
00170         }
00171 
00172         for(i = 0, pos = heap->buffer; i < sz; i++, pos += elmsz) {
00173                 if ( (ret = eval( i, pos, elmsz, context )) != 0) {
00174                         if (retval) {
00175                                 *retval = ret;
00176                         }
00177                         return i;
00178                 }
00179         }
00180         return -1;
00181 }
00182 
00183 /**
00184  * @}
00185  */ 
00186 
00187 #ifdef  __cplusplus
00188 }
00189 #endif
00190 
00191 #endif
00192