QuantHash.c 7.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336
  1. /*
  2. * The Python Imaging Library
  3. * $Id$
  4. *
  5. * hash tables used by the image quantizer
  6. *
  7. * history:
  8. * 98-09-10 tjs Contributed
  9. * 98-12-29 fl Added to PIL 1.0b1
  10. *
  11. * Written by Toby J Sargeant <tjs@longford.cs.monash.edu.au>.
  12. *
  13. * Copyright (c) 1998 by Toby J Sargeant
  14. * Copyright (c) 1998 by Secret Labs AB
  15. *
  16. * See the README file for information on usage and redistribution.
  17. */
  18. #include <stdio.h>
  19. #include <stdlib.h>
  20. #include <string.h>
  21. #include <math.h>
  22. #include "QuantHash.h"
  23. typedef struct _HashNode {
  24. struct _HashNode *next;
  25. HashKey_t key;
  26. HashVal_t value;
  27. } HashNode;
  28. struct _HashTable {
  29. HashNode **table;
  30. uint32_t length;
  31. uint32_t count;
  32. HashFunc hashFunc;
  33. HashCmpFunc cmpFunc;
  34. void *userData;
  35. };
  36. #define MIN_LENGTH 11
  37. #define RESIZE_FACTOR 3
  38. static int
  39. _hashtable_insert_node(HashTable *, HashNode *, int, int, CollisionFunc);
  40. HashTable *
  41. hashtable_new(HashFunc hf, HashCmpFunc cf) {
  42. HashTable *h;
  43. h = malloc(sizeof(HashTable));
  44. if (!h) {
  45. return NULL;
  46. }
  47. h->hashFunc = hf;
  48. h->cmpFunc = cf;
  49. h->length = MIN_LENGTH;
  50. h->count = 0;
  51. h->userData = NULL;
  52. h->table = malloc(sizeof(HashNode *) * h->length);
  53. if (!h->table) {
  54. free(h);
  55. return NULL;
  56. }
  57. memset(h->table, 0, sizeof(HashNode *) * h->length);
  58. return h;
  59. }
  60. static uint32_t
  61. _findPrime(uint32_t start, int dir) {
  62. static int unit[] = {0, 1, 0, 1, 0, 0, 0, 1, 0, 1, 0, 1, 0, 1, 0, 0};
  63. uint32_t t;
  64. while (start > 1) {
  65. if (!unit[start & 0x0f]) {
  66. start += dir;
  67. continue;
  68. }
  69. for (t = 2; t < sqrt((double)start); t++) {
  70. if (!start % t) {
  71. break;
  72. }
  73. }
  74. if (t >= sqrt((double)start)) {
  75. break;
  76. }
  77. start += dir;
  78. }
  79. return start;
  80. }
  81. static void
  82. _hashtable_rehash(HashTable *h, CollisionFunc cf, uint32_t newSize) {
  83. HashNode **oldTable = h->table;
  84. uint32_t i;
  85. HashNode *n, *nn;
  86. uint32_t oldSize;
  87. oldSize = h->length;
  88. h->table = malloc(sizeof(HashNode *) * newSize);
  89. if (!h->table) {
  90. h->table = oldTable;
  91. return;
  92. }
  93. h->length = newSize;
  94. h->count = 0;
  95. memset(h->table, 0, sizeof(HashNode *) * h->length);
  96. for (i = 0; i < oldSize; i++) {
  97. for (n = oldTable[i]; n; n = nn) {
  98. nn = n->next;
  99. _hashtable_insert_node(h, n, 0, 0, cf);
  100. }
  101. }
  102. free(oldTable);
  103. }
  104. static void
  105. _hashtable_resize(HashTable *h) {
  106. uint32_t newSize;
  107. uint32_t oldSize;
  108. oldSize = h->length;
  109. newSize = oldSize;
  110. if (h->count * RESIZE_FACTOR < h->length) {
  111. newSize = _findPrime(h->length / 2 - 1, -1);
  112. } else if (h->length * RESIZE_FACTOR < h->count) {
  113. newSize = _findPrime(h->length * 2 + 1, +1);
  114. }
  115. if (newSize < MIN_LENGTH) {
  116. newSize = oldSize;
  117. }
  118. if (newSize != oldSize) {
  119. _hashtable_rehash(h, NULL, newSize);
  120. }
  121. }
  122. static int
  123. _hashtable_insert_node(
  124. HashTable *h, HashNode *node, int resize, int update, CollisionFunc cf) {
  125. uint32_t hash = h->hashFunc(h, node->key) % h->length;
  126. HashNode **n, *nv;
  127. int i;
  128. for (n = &(h->table[hash]); *n; n = &((*n)->next)) {
  129. nv = *n;
  130. i = h->cmpFunc(h, nv->key, node->key);
  131. if (!i) {
  132. if (cf) {
  133. nv->key = node->key;
  134. cf(h, &(nv->key), &(nv->value), node->key, node->value);
  135. free(node);
  136. return 1;
  137. } else {
  138. nv->key = node->key;
  139. nv->value = node->value;
  140. free(node);
  141. return 1;
  142. }
  143. } else if (i > 0) {
  144. break;
  145. }
  146. }
  147. if (!update) {
  148. node->next = *n;
  149. *n = node;
  150. h->count++;
  151. if (resize) {
  152. _hashtable_resize(h);
  153. }
  154. return 1;
  155. } else {
  156. return 0;
  157. }
  158. }
  159. static int
  160. _hashtable_insert(HashTable *h, HashKey_t key, HashVal_t val, int resize, int update) {
  161. HashNode **n, *nv;
  162. HashNode *t;
  163. int i;
  164. uint32_t hash = h->hashFunc(h, key) % h->length;
  165. for (n = &(h->table[hash]); *n; n = &((*n)->next)) {
  166. nv = *n;
  167. i = h->cmpFunc(h, nv->key, key);
  168. if (!i) {
  169. nv->value = val;
  170. return 1;
  171. } else if (i > 0) {
  172. break;
  173. }
  174. }
  175. if (!update) {
  176. t = malloc(sizeof(HashNode));
  177. if (!t) {
  178. return 0;
  179. }
  180. t->next = *n;
  181. *n = t;
  182. t->key = key;
  183. t->value = val;
  184. h->count++;
  185. if (resize) {
  186. _hashtable_resize(h);
  187. }
  188. return 1;
  189. } else {
  190. return 0;
  191. }
  192. }
  193. int
  194. hashtable_insert_or_update_computed(
  195. HashTable *h, HashKey_t key, ComputeFunc newFunc, ComputeFunc existsFunc) {
  196. HashNode **n, *nv;
  197. HashNode *t;
  198. int i;
  199. uint32_t hash = h->hashFunc(h, key) % h->length;
  200. for (n = &(h->table[hash]); *n; n = &((*n)->next)) {
  201. nv = *n;
  202. i = h->cmpFunc(h, nv->key, key);
  203. if (!i) {
  204. if (existsFunc) {
  205. existsFunc(h, nv->key, &(nv->value));
  206. } else {
  207. return 0;
  208. }
  209. return 1;
  210. } else if (i > 0) {
  211. break;
  212. }
  213. }
  214. t = malloc(sizeof(HashNode));
  215. if (!t) {
  216. return 0;
  217. }
  218. t->key = key;
  219. t->next = *n;
  220. *n = t;
  221. if (newFunc) {
  222. newFunc(h, t->key, &(t->value));
  223. } else {
  224. free(t);
  225. return 0;
  226. }
  227. h->count++;
  228. _hashtable_resize(h);
  229. return 1;
  230. }
  231. int
  232. hashtable_insert(HashTable *h, HashKey_t key, HashVal_t val) {
  233. return _hashtable_insert(h, key, val, 1, 0);
  234. }
  235. void
  236. hashtable_foreach_update(HashTable *h, IteratorUpdateFunc i, void *u) {
  237. HashNode *n;
  238. uint32_t x;
  239. if (h->table) {
  240. for (x = 0; x < h->length; x++) {
  241. for (n = h->table[x]; n; n = n->next) {
  242. i(h, n->key, &(n->value), u);
  243. }
  244. }
  245. }
  246. }
  247. void
  248. hashtable_foreach(HashTable *h, IteratorFunc i, void *u) {
  249. HashNode *n;
  250. uint32_t x;
  251. if (h->table) {
  252. for (x = 0; x < h->length; x++) {
  253. for (n = h->table[x]; n; n = n->next) {
  254. i(h, n->key, n->value, u);
  255. }
  256. }
  257. }
  258. }
  259. void
  260. hashtable_free(HashTable *h) {
  261. HashNode *n, *nn;
  262. uint32_t i;
  263. if (h->table) {
  264. for (i = 0; i < h->length; i++) {
  265. for (n = h->table[i]; n; n = nn) {
  266. nn = n->next;
  267. free(n);
  268. }
  269. }
  270. free(h->table);
  271. }
  272. free(h);
  273. }
  274. void
  275. hashtable_rehash_compute(HashTable *h, CollisionFunc cf) {
  276. _hashtable_rehash(h, cf, h->length);
  277. }
  278. int
  279. hashtable_lookup(const HashTable *h, const HashKey_t key, HashVal_t *valp) {
  280. uint32_t hash = h->hashFunc(h, key) % h->length;
  281. HashNode *n;
  282. int i;
  283. for (n = h->table[hash]; n; n = n->next) {
  284. i = h->cmpFunc(h, n->key, key);
  285. if (!i) {
  286. *valp = n->value;
  287. return 1;
  288. } else if (i > 0) {
  289. break;
  290. }
  291. }
  292. return 0;
  293. }
  294. uint32_t
  295. hashtable_get_count(const HashTable *h) {
  296. return h->count;
  297. }
  298. void *
  299. hashtable_get_user_data(const HashTable *h) {
  300. return h->userData;
  301. }
  302. void *
  303. hashtable_set_user_data(HashTable *h, void *data) {
  304. void *r = h->userData;
  305. h->userData = data;
  306. return r;
  307. }