Hash algorithm for PHP

xiaoxiao2021-03-06  36

/ * * Header file * Description: This implementation does not save objects, only save objects * / # ifndef _hash_h # define _hash_h # ifdef __cplusplusextern "c" {#ENDIF

Typedef struct taghashbucket hashbucket, * lphashbucket; typedef struct taghashtable hashtable, * lphashtable

struct tagHASHBUCKET {unsigned long h; unsigned int key_length; void * data; LPHASHBUCKET next; LPHASHBUCKET previous; LPHASHBUCKET conflict_next; LPHASHBUCKET conflict_previous; char key [1];};

Typedef unsigned long (* hash_func_t) (char *, unsigned int);

struct tagHASHTABLE {unsigned int table_size; unsigned int size_index; unsigned int elements; hash_func_t hash; LPHASHBUCKET p; LPHASHBUCKET head; LPHASHBUCKET tail; LPHASHBUCKET * buckets;};

extern int hash_create (LPHASHTABLE, unsigned int, hash_func_t); extern int hash_entry (LPHASHTABLE, char *, unsigned int, void *); extern int hash_find (LPHASHTABLE, char *, unsigned int, void **); extern int hash_update (LPHASHTABLE , char *, unsigned int, void *); extern int hash_remove (LPHASHTABLE, char *, unsigned int); extern int hash_destroy (LPHASHTABLE); # ifdef __cplusplus}; # endif # endif / * * HASH implemented * / # include < STDLIB.H> #include #include "main.h"

Static unsigned int size_table [] = {5, 11, 19, 53, 107, 223, 463, 983, 1979, 3,2531, 654,09,87, 2,62237, 5,24521, 1048793, 5,245,1, 10,487,03, 20,973,87, 4,194103, 8388857, 16777447, 335554201, 67108961, 134217487, 268435697, 536870683, 1073741621, 2147483399}; # define counts_of_size_table (sizeof (size) / sizeof (size_table [0]))

Static unsigned longhashpjw (char * key, unsigned int key_length) {UNSIGNED Long H, g; char * p;

H = 0; p = key key_length; while (key > 24); h = h ^ g;}} Return H;

Static inthash_do_rehash (lphashtable pHT) {lphashbucket p; unsigned int index;

MEMSET (PHT-> BUCKETS, 0, SIZEOF (LPHASHBUCKET) * SIZE_TABLE [PHT-> SIZE_INDEX]); for (p = pht-> head; p; p = p-> next) {index = p-> h% pht -> Table_size; p-> conflict_next = 0; p-> conflict_previous = pht-> buckets [index]; if (p-> conflict_previous) {p-> conflict_previous-> conflict_next = p;} pht-> buckets [index] = P;}

Return 0;}

Static inthash_do_resize (lphashtable pht) {lphashbucket * pp;

IF (PHT-> SIZE_INDEX <(unsigned int) counts_of_size_table - 1) {pp = (lphashbucket *) Realloc (pht-> buckets, size_table [pht-> size_index 1] * sizeof (lphashbucket)); if (pp) { PHT-> buckets = PP; pht-> size_index ; pht-> table_size = size_table [pht-> size_index]; haveh_do_rehash (pHT); return 0;} return -1;}

Return 0;}

INTHASH_CREATE (LPHASHTABLE PHT, UNSIGNED INT SIZE, HASH_FUNC_T HASH) {INT I;

For (i = 0; i size_index = i; break;}} if (i == counts_of_size_table ) {size = size_table [COUNTS_OF_SIZE_TABLE - 1]; pht-> size_index = COUNTS_OF_SIZE_TABLE - 1;}! pht-> buckets = (LPHASHBUCKET *) calloc (size, sizeof (LPHASHBUCKET)); if (pht-> buckets) {return -1;} pht-> hash = Hash? Hash: hashpjw; pht-> Elements = 0; pht-> head = 0; pht-> p = 0; pht-> tail = 0; pHT-> Table_size = size;

Return 0;}

INTHASH_ENTRY (LPHASHTABLE PHT, CHAR * Key, Unsigned Int Key_LENGTH, VOID * DATA) {Unsigned Long H; UNSIGNED INDEX; LPHASHBUCKET P;

H = pht-> hash (key, key_length); index = h% pht-> table_size;

For (p = pht-> buckets [index]; p; p = p-> conflict_previous) {if (p-> h == h && p-> key_length == key_length) {if (! Memcmp (P-> Key , Key, Key_Length) {RETURN -1;}}}

P = (LPHASHBUCKET) Malloc (Sizeof (Hashbucket) - 1 Key_Length); if (! p) {return -1;} Memcpy (P-> Key, Key, Key_Length); P-> Key_Length = Key_Length; P-> H = h; p-> Data = data;

P-> conflict_next = 0; P-> conflict_previous = pht-> buckets [index]; if (p-> conflict_previous) {p-> confiosct_previous-> confiict_next = p;} P-> previous = pht-> tail; P -> Next = 0; pht-> tail = p; if (p-> previous) {p-> previous-> next = p;} if (! pHt-> head) {pht-> head = p;} pht -> buckets [index] = p; pht-> Elements; if (pht-> elements> pht-> table_size) {hash_do_resize (pht);}

Return 0;}

INTHASH_FIND (LPHASHTABLE PHT, Char * Key, Unsigned Int Key_LENGTH, VOID ** DATA) {Unsigned Long H; UNSIGNED INDEX; LPHASHBUCKET P;

H = pht-> hash (key, key_length); index = h% pht-> table_size;

For (p = pht-> buckets [index]; p; p = p-> confict_previous) {if (p-> h == h && p-> key_length == key_length &&! memcmp (p-> key, key, Key_Length)) {* data = p-> data; return 0;}}

Return -1;

INTHASH_REMOVE (LPHASHTABLE PHT, CHAR * Key, unsigned int key_length) {Unsigned long h; unsigned int index; lphashbucket p;

H = pht-> hash (key, key_length); index = h% pht-> table_size;

For (p = pht-> buckets [index]; p; p = p-> confict_previous) {if (p-> h == h && p-> key_length == key_length &&! memcmp (p-> key, key, key_length)) {if (p-> conflict_previous) {p-> conflict_previous-> conflict_next = p-> conflict_next;} if (p-> conflict_next) {p-> conflict_next-> conflict_previous = p-> conflict_previous;} if ( P-> previous) {p-> prepious-> next = p-> next;} if (p-> next) {p-> next-> previous = p-> previous;} if (pht-> buckets [index ] == p) {pht-> BUCKETS [INDEX] = P-> conflict_previous;} if (pht-> head == p) {pht-> head = p-> next;} if (pht-> tail == p) {pht-> tail = p-> previous;} --pht-> elements; free (p); return 0; }

Return -1;

INTHASH_UPDATE (LPHASHTABLE PHT, CHAR * Key, Unsigned Int Key_LENGTH, VOID * DATA) {UNSIGNED Long H; unsigned int index; lphashbucket p;

H = pht-> hash (key, key_length); index = h% pht-> table_size;

For (p = pht-> buckets [index]; p; p = p-> confict_previous) {if (p-> h == h && p-> key_length == key_length &&! memcmp (p-> key, key, Key_Length)) {P-> Data = DATA; RETURN 0;}}

Return -1;} inthash_destroy (lphashbucket p, q; p = pht-> head; while (p) {q = p; p = p-> next; free (q);} free (pht-> Buckets;

Return 0;}

转载请注明原文地址:https://www.9cbs.com/read-66638.html

New Post(0)