00001 /** @file psList.h 00002 * @brief Support for doubly linked lists 00003 * 00004 * @author Robert Lupton, Princeton University 00005 * @author Robert Daniel DeSonia, MHPCC 00006 * 00007 * @ingroup LinkedList 00008 * 00009 * @version $Revision: 1.1.1.1 $ $Name: $ 00010 * @date $Date: 2005/06/15 21:08:12 $ 00011 * 00012 * Copyright 2004-2005 Maui High Performance Computing Center, University of Hawaii 00013 */ 00014 00015 #ifndef PS_LIST_H 00016 #define PS_LIST_H 00017 00018 #include <pthread.h> // we need a mutex to make this stuff thread safe. 00019 00020 #include "psCompare.h" 00021 #include "psArray.h" 00022 00023 /** @addtogroup LinkedList 00024 * @{ 00025 */ 00026 00027 /** Special values of index into list 00028 * 00029 * This list of possible list position values should be contiguous non-positive values ending with 00030 * PS_LIST_UNKNOWN. Any value less-than-or-equal-to PS_LIST_UNKNOWN is considered a undefined position. 00031 * 00032 */ 00033 enum { 00034 PS_LIST_HEAD = 0, ///< at head 00035 PS_LIST_TAIL = -1, ///< at tail 00036 }; 00037 00038 /** Doubly-linked list element */ 00039 typedef struct psListElem 00040 { 00041 struct psListElem* prev; ///< previous link in list 00042 struct psListElem* next; ///< next link in list 00043 psPtr data; ///< real data item 00044 } 00045 psListElem; 00046 00047 /** The psList Linked list structure. User should not allocate this struct 00048 * directly; rather the psListAlloc should be used. 00049 * 00050 * @see psListAlloc 00051 */ 00052 typedef struct 00053 { 00054 psU32 size; ///< number of elements on list 00055 psListElem* head; ///< first element on list (may be NULL) 00056 psListElem* tail; ///< last element on list (may be NULL) 00057 psArray* iterators; 00058 ///< array of all iterators associated with this list. First iterator is 00059 ///< used internally to improve performance when using indexed access, all 00060 ///< others are user-level iterators created by psListIteratorAlloc. 00061 00062 pthread_mutex_t lock; ///< mutex to lock a node during changes 00063 } 00064 psList; 00065 00066 /** The psList iterator structure. This should be allocated via 00067 * psListIteratorAlloc and not directly. 00068 * 00069 * The life span of a psListIterator object is ended by either a psFree 00070 * of this structure OR psFree of the psList in which it operates on. 00071 * 00072 * @see psListIteratorAlloc, psListIteratorSet, psListGetAndIncrement, psListGetAndDecrement 00073 */ 00074 typedef struct 00075 { 00076 psList* list; ///< List iterator to works on 00077 psListElem* cursor; ///< current cursor position 00078 int index; ///< the index number in the list 00079 bool offEnd; ///< Iterator off the end? 00080 bool mutable; ///< Is it permissible to modify the list? 00081 } 00082 psListIterator; 00083 00084 00085 /** Creates a psList linked list object. 00086 * 00087 * @return psList* A new psList object. 00088 */ 00089 psList* psListAlloc( 00090 psPtr data 00091 ///< initial data item; may be NULL if no an empty psList is desired 00092 ) 00093 ; 00094 00095 /** Creates a psListIterator object and associates it with a psList. 00096 * 00097 * @return psListIterator* A new psListIterator object. 00098 */ 00099 psListIterator* psListIteratorAlloc( 00100 psList* list, ///< the psList to iterate with 00101 int location, ///< the initial starting point. 00102 ///< This can be a numeric index, PS_LIST_HEAD, or PS_LIST_TAIL. 00103 bool mutable ///< Is it permissible to modify list? 00104 ); 00105 00106 /** Set the iterator of the list to a given position. If location is invalid the 00107 * iterator position is not changed. 00108 * 00109 * @return psBool TRUE if iterator successfully set, otherwise FALSE. 00110 */ 00111 psBool psListIteratorSet( 00112 psListIterator* iterator, ///< list iterator 00113 int location ///< index number, PS_LIST_HEAD, or PS_LIST_TAIL 00114 ); 00115 00116 /** Adds an element to a psList at position given. 00117 * 00118 * @return psBool TRUE if item was successfully added, otherwise FALSE. 00119 */ 00120 psBool psListAdd( 00121 psList* list, ///< list to add item to 00122 psS32 location, ///< index, PS_LIST_HEAD, PS_LIST_TAIL, or numbered location. 00123 psPtr data ///< data item to add. If NULL, list is not modified. 00124 ); 00125 00126 /** Adds an data item to a psList at position just after the list position given 00127 * 00128 * @return psBool TRUE if item was successfully added, otherwise FALSE. 00129 */ 00130 psBool psListAddAfter( 00131 psListIterator* list, ///< list position to add item to 00132 psPtr data ///< data item to add. If NULL, list is not modified. 00133 ); 00134 00135 /** Adds an data item to a psList at position just before the list position given 00136 * 00137 * @return psBool TRUE if item was successfully added, otherwise FALSE. 00138 */ 00139 psBool psListAddBefore( 00140 psListIterator* list, ///< list position to add item to 00141 psPtr data ///< data item to add. If NULL, list is not modified. 00142 ); 00143 00144 /** Remove an item at the specified location from a list. 00145 * 00146 * @return psBool TRUE if element is successfully removed, otherwise FALSE. 00147 */ 00148 psBool psListRemove( 00149 psList* list, ///< list to remove element from 00150 psS32 location ///< index of item 00151 ); 00152 00153 /** Remove an item from a list. 00154 * 00155 * @return psBool TRUE if element is successfully removed, otherwise FALSE. 00156 */ 00157 psBool psListRemoveData( 00158 psList* list, ///< list to remove element from 00159 psPtr data ///< data item to find and remove 00160 ); 00161 00162 /** Retrieve an item from a list. 00163 * 00164 * @return psPtr the item corresponding to the location parameter. If 00165 * location is invalid (e.g., a numbered index greater 00166 * than the list size or if the list is empty), a 00167 * NULL is returned. 00168 */ 00169 psPtr psListGet( 00170 psList* list, ///< list to retrieve element from 00171 psS32 location ///< index number, PS_LIST_HEAD, or PS_LIST_TAIL 00172 ); 00173 00174 /** Position the specified iterator to the next item in list. 00175 * 00176 * @return psPtr the data item at the original iterator position or NULL if the 00177 * iterator went past the end of the list. 00178 */ 00179 psPtr psListGetAndIncrement( 00180 psListIterator* iterator ///< iterator to move 00181 ); 00182 00183 /** Position the specified iterator to the previous item in list. 00184 * 00185 * @return psPtr the data item at the original iterator position or NULL if the 00186 * iterator went past the beginning of the list. 00187 */ 00188 psPtr psListGetAndDecrement( 00189 psListIterator* iterator ///< iterator to move 00190 ); 00191 00192 /** Convert a linked list to an array 00193 * 00194 * @return psArray* A new psArray populated with elements from the list, 00195 * or NULL if the given dlist parameter is NULL. 00196 */ 00197 psArray* psListToArray( 00198 psList* dlist ///< List to convert 00199 ); 00200 00201 /** Convert array to a doubly-linked list 00202 * 00203 * @return psList* A new psList populated with elements formt the psArray, 00204 * or NULL is the given arr parameter is NULL. 00205 */ 00206 psList* psArrayToList( 00207 psArray* arr ///< vector to convert 00208 ); 00209 00210 /** Sort a list via a comparison function. 00211 * 00212 * The comparison function must return an integer less than, equal to, or 00213 * greater than zero if the first argument is considered to be respectively 00214 * less than, equal to, or greater than the second. 00215 * 00216 * If two members compare as equal, their order in the sorted array is 00217 * undefined. 00218 * 00219 * @return psList* Sorted list. 00220 */ 00221 psList* psListSort( 00222 psList* list, ///< the list to sort 00223 psComparePtrFcn compare ///< the comparison function 00224 ); 00225 00226 /// @} End of DataGroup Functions 00227 00228 #endif // #ifndef PS_LIST_H 00229
1.4.1