Go to the documentation of this file.00001 #ifndef __HashTable_H__
00002 #define __HashTable_H__
00003
00004
00005 #include <stddef.h>
00006 #include <assert.h>
00007 #include <stdio.h>
00008
00009 #include <map>
00010 #include <vector>
00011 #include <iostream>
00012
00013
00014 #define xDEBUG(flag,code) { if (flag) {code; fflush(stdout);} }
00015 #define DEB_HashTable 0
00016
00017 namespace stlCompatibility {
00018
00019 using namespace std;
00020
00021
00022 template <class _Key> struct Hash { };
00023
00024 inline size_t hashString(const char* __s)
00025 {
00026 unsigned long __h = 0;
00027 for ( ; *__s; ++__s)
00028 __h = 5*__h + *__s;
00029
00030 return size_t(__h);
00031 }
00032 template<> struct Hash<char*>
00033 {
00034 size_t operator()(const char* __s) const { return hashString(__s); }
00035 };
00036 template<> struct Hash<const char*>
00037 {
00038 size_t operator()(const char* __s) const { return hashString(__s); }
00039 };
00040 template<> struct Hash<char> {
00041 size_t operator()(char __x) const { return __x; }
00042 };
00043 template<> struct Hash<unsigned char> {
00044 size_t operator()(unsigned char __x) const { return __x; }
00045 };
00046 template<> struct Hash<signed char> {
00047 size_t operator()(unsigned char __x) const { return __x; }
00048 };
00049 template<> struct Hash<short> {
00050 size_t operator()(short __x) const { return __x; }
00051 };
00052 template<> struct Hash<unsigned short> {
00053 size_t operator()(unsigned short __x) const { return __x; }
00054 };
00055 template<> struct Hash<int> {
00056 size_t operator()(int __x) const { return __x; }
00057 };
00058 template<> struct Hash<unsigned int> {
00059 size_t operator()(unsigned int __x) const { return __x; }
00060 };
00061 template<> struct Hash<long> {
00062 size_t operator()(long __x) const { return __x; }
00063 };
00064 template<> struct Hash<unsigned long> {
00065 size_t operator()(unsigned long __x) const { return __x; }
00066 };
00067
00068
00069
00070 template <class Key, class Value,
00071 class KeyHash = Hash<Key>,
00072 class KeyEq = equal_to<Key> >
00073 class HashTable {
00074 public:
00075 typedef Key KeyType;
00076 typedef Value ValueType;
00077 typedef KeyHash hasher;
00078 typedef KeyEq key_equal;
00079
00080 typedef pair<Key, Value> value_type;
00081 typedef pair<Key, Value> KeyValuePair;
00082 typedef pair<const Value, bool> ValueBoolPair;
00083
00084 private:
00085 typedef vector<KeyValuePair> KeyValuePairVector;
00086 typedef typename KeyValuePairVector::iterator KeyValuePairVectorIterator;
00087 typedef map<size_t, KeyValuePairVector, less<size_t> > Ht;
00088 typedef typename Ht::iterator HtIterator;
00089 typedef typename Ht::const_iterator HtConstIterator;
00090
00091 Ht ht;
00092 size_t _size;
00093 KeyHash keyHash;
00094 KeyEq keyEq;
00095
00096 public:
00097 KeyHash & hashClass() { return keyHash; }
00098 KeyEq & eqClass() { return keyEq; }
00099
00100 HashTable() {
00101 _size = 0;
00102 }
00103
00104 virtual ~HashTable() {
00105 clear();
00106 }
00107
00108 public:
00109 void clear() {
00110 if (size() == 0) return;
00111 HtIterator htIterator;
00112 for ( htIterator = ht.begin();
00113 htIterator != ht.end();
00114 htIterator ++ ) {
00115 htIterator->second.clear();
00116 }
00117 ht.clear();
00118 _size = 0;
00119 }
00120
00121 size_t size() const {
00122 return _size;
00123 }
00124
00125 bool empty() const {
00126 return (_size == 0);
00127 }
00128
00129 size_t count(const Key& k) const {
00130 size_t h = keyHash(k);
00131 HtConstIterator htIterator = ht.find(h);
00132 if (htIterator == ht.end()) return 0;
00133 return htIterator->second.size();
00134 }
00135
00136 ValueBoolPair find(const Key& k) const {
00137 size_t h = keyHash(k);
00138 HtConstIterator htIterator = ht.find(h);
00139 if (htIterator == ht.end()) return ValueBoolPair((const Value)NULL, false);
00140
00141 const KeyValuePairVector& kvpv = htIterator->second;
00142 typename KeyValuePairVector::const_iterator kvpvIterator;
00143 for ( kvpvIterator = kvpv.begin();
00144 kvpvIterator != kvpv.end();
00145 kvpvIterator ++ ) {
00146 const Key& kk = kvpvIterator->first;
00147 if (keyEq(k, kk) == true) return ValueBoolPair(kvpvIterator->second, true);
00148 }
00149 return ValueBoolPair((const Value)NULL, false);
00150 }
00151
00152 ValueBoolPair insert(const KeyValuePair& p) {
00153 size_t h = keyHash(p.first);
00154 HtIterator htIterator = ht.find(h);
00155 if (htIterator != ht.end()) {
00156 KeyValuePairVector& kvpv = htIterator->second;
00157 xDEBUG(DEB_HashTable,
00158 printf("insert: h=%u, ht.size()=%u, ht[h].size()=%u\n", h, ht.size(), kvpv.size());
00159 );
00160 KeyValuePairVectorIterator kvpvIterator;
00161 for ( kvpvIterator = kvpv.begin();
00162 kvpvIterator != kvpv.end();
00163 kvpvIterator ++ ) {
00164 Key& kk = kvpvIterator->first;
00165 if (keyEq(p.first, kk) == true) {
00166 return ValueBoolPair(kvpvIterator->second, false);
00167 }
00168 }
00169 kvpv.push_back(p);
00170 } else {
00171 xDEBUG(DEB_HashTable,
00172 printf("insert: h=%u, ht.size()=%u, ht[h].size()=%u\n", h, ht.size(), 0));
00173 KeyValuePairVector kvpv;
00174 kvpv.push_back(p);
00175 pair<HtIterator, bool> tmp1 = ht.insert(typename Ht::value_type(h, kvpv));
00176 assert(tmp1.second == true);
00177 }
00178 _size ++;
00179 return ValueBoolPair(p.second, true);
00180 }
00181
00182 ValueBoolPair erase(const Key& k) {
00183 size_t h = keyHash(k);
00184 xDEBUG(DEB_HashTable, printf("erase: h=%u\n", h));
00185
00186 HtIterator htIterator = ht.find(h);
00187 if (htIterator == ht.end()) return ValueBoolPair((const Value)NULL, false);
00188
00189 KeyValuePairVector& kvpv = htIterator->second;
00190 KeyValuePairVectorIterator kvpvIterator;
00191 for ( kvpvIterator = kvpv.begin();
00192 kvpvIterator != kvpv.end();
00193 kvpvIterator ++ ) {
00194 Key& kk = kvpvIterator->first;
00195 if (keyEq(k, kk) == true) {
00196 Value v = kvpvIterator->second;
00197 kvpv.erase(kvpvIterator);
00198 _size --;
00199 if (kvpv.empty()) ht.erase(htIterator);
00200 return ValueBoolPair(v, true);
00201 }
00202 }
00203
00204 assert(false);
00205 return ValueBoolPair((const Value)NULL, false);
00206 }
00207
00208 ValueBoolPair modify(const KeyValuePair& p) {
00209 assert(false);
00210 return ValueKeyPair((const Value)NULL, false);
00211 }
00212
00213
00214
00215 class ForAllAction {
00216 public:
00217 virtual void handle(const Key k, Value &v) = 0;
00218 };
00219
00220
00221 void forAll(ForAllAction & action) {
00222 HtIterator htIterator;
00223 KeyValuePairVectorIterator kvpvIterator;
00224
00225 for ( htIterator = ht.begin();
00226 htIterator != ht.end();
00227 htIterator ++ ) {
00228 KeyValuePairVector& kvpv = htIterator->second;
00229 for ( kvpvIterator = kvpv.begin();
00230 kvpvIterator != kvpv.end();
00231 kvpvIterator ++ ) {
00232 const Key& k = kvpvIterator->first;
00233 Value& v = kvpvIterator->second;
00234
00235 action.handle(k, v);
00236 }
00237 }
00238 }
00239 };
00240
00241 }
00242
00243 #endif
00244
00245