mirror of
https://git.code.sf.net/p/quake/quakeforge
synced 2025-02-18 09:51:40 +00:00
[hash] Add a couple of data-oriented functions
Hash_Select returns a list of elements that match a given criterion (select callback returning non-0). Hash_ForEach simply calls a function for every element.
This commit is contained in:
parent
df4116a55d
commit
8bd626a3e4
2 changed files with 65 additions and 0 deletions
|
@ -38,6 +38,8 @@
|
||||||
|
|
||||||
typedef struct hashtab_s hashtab_t;
|
typedef struct hashtab_s hashtab_t;
|
||||||
typedef struct hashlink_s hashlink_t;
|
typedef struct hashlink_s hashlink_t;
|
||||||
|
typedef int (*hash_select_t) (void *ele, void *data);
|
||||||
|
typedef void (*hash_action_t) (void *ele, void *data);
|
||||||
|
|
||||||
/** create a new hash table.
|
/** create a new hash table.
|
||||||
\param tsize table size. larger values will give better distribution, but
|
\param tsize table size. larger values will give better distribution, but
|
||||||
|
@ -213,6 +215,32 @@ size_t Hash_NumElements (hashtab_t *tab) __attribute__((pure));
|
||||||
*/
|
*/
|
||||||
void **Hash_GetList (hashtab_t *tab);
|
void **Hash_GetList (hashtab_t *tab);
|
||||||
|
|
||||||
|
/** list of all matching elements in the table.
|
||||||
|
\param tab the table to search
|
||||||
|
\param select function that tests for a match. The expected return value
|
||||||
|
is 0 for no match, non-zero for a match.
|
||||||
|
\param data context data passed to the \a select function
|
||||||
|
\return a null terminated list of element pointers for all matchin
|
||||||
|
elements in the table
|
||||||
|
\note it is the caller's responsibilty to free() the list.
|
||||||
|
|
||||||
|
returned list is guaranteed to be in reverse order of insertion for
|
||||||
|
elements with the same key. ie, deleting items from the list in list order
|
||||||
|
will delete the correct items.
|
||||||
|
*/
|
||||||
|
void **Hash_Select (hashtab_t *tab, hash_select_t select, void *data);
|
||||||
|
|
||||||
|
|
||||||
|
/** call a function for all elements in the table.
|
||||||
|
\param tab the table to search
|
||||||
|
\param action function to call for each elelemnt
|
||||||
|
\param data context data passed to the \a action function
|
||||||
|
|
||||||
|
call order is guaranteed to be in reverse order of insertion for
|
||||||
|
elements with the same key
|
||||||
|
*/
|
||||||
|
void Hash_ForEach (hashtab_t *tab, hash_action_t action, void *data);
|
||||||
|
|
||||||
/** dump statistics about the hash table
|
/** dump statistics about the hash table
|
||||||
\param tab the table to dump
|
\param tab the table to dump
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -447,6 +447,43 @@ Hash_GetList (hashtab_t *tab)
|
||||||
return list;
|
return list;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
VISIBLE void **
|
||||||
|
Hash_Select (hashtab_t *tab, hash_select_t select, void *data)
|
||||||
|
{
|
||||||
|
void **list;
|
||||||
|
void **l;
|
||||||
|
size_t ind;
|
||||||
|
|
||||||
|
l = list = malloc ((tab->num_ele + 1) * sizeof (void *));
|
||||||
|
if (!list)
|
||||||
|
return 0;
|
||||||
|
for (ind = 0; ind < tab->tab_size; ind++) {
|
||||||
|
hashlink_t *lnk;
|
||||||
|
|
||||||
|
for (lnk = tab->tab[ind]; lnk; lnk = lnk->next) {
|
||||||
|
if (select (lnk->data, data)) {
|
||||||
|
*l++ = lnk->data;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
*l++ = 0;
|
||||||
|
return list;
|
||||||
|
}
|
||||||
|
|
||||||
|
VISIBLE void
|
||||||
|
Hash_ForEach (hashtab_t *tab, hash_action_t action, void *data)
|
||||||
|
{
|
||||||
|
size_t ind;
|
||||||
|
|
||||||
|
for (ind = 0; ind < tab->tab_size; ind++) {
|
||||||
|
hashlink_t *lnk;
|
||||||
|
|
||||||
|
for (lnk = tab->tab[ind]; lnk; lnk = lnk->next) {
|
||||||
|
action (lnk->data, data);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static inline double
|
static inline double
|
||||||
sqr (double x)
|
sqr (double x)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue