Catos Engine (Source) 0.0.1
Lightweight Game engine
Loading...
Searching...
No Matches
hashmap.h
Go to the documentation of this file.
1//
2// Created by allos on 8/29/2024.
3//
4
5#ifndef CATOS_HASHMAP_H
6#define CATOS_HASHMAP_H
7
8namespace catos {
9
10 //std::exception kiss my ass >:(
12 const char* what() {
13 return "No Item found with that key\n";
14 }
15 };
16
18 const char* what() {
19 return "No Bucket found with that key\n";
20 }
21 };
22
23
24
25
26 template<typename K, typename V>
27 class hashnode {
28 public:
29
30 hashnode(const K& key, const V& value) : key(key), value(value) {}
31
32
33 K getKey() const {
34 return key;
35 }
36
37 V getValue() const {
38 return value;
39 }
40
41 hashnode* getNext() const{
42 return next;
43 }
44
45 void setValue(V newVal) {
46 value = newVal;
47 }
48
49 void setNext(hashnode* newNext) {
50 next = newNext;
51 }
52
53 private:
54 K key;
55 V value;
56 hashnode* next = nullptr;
57
58 };
59
60 template<typename K>
61 struct HashFunc {
62 size_t operator()(const K& key, int Size) const {
63 return static_cast<size_t>(key) % Size;
64 }
65 };
66
67
68
74 template<typename K, typename V, typename F = HashFunc<K>>
75 class hashmap {
76
77 public:
78
80 hashmap(int startSize = 8) : maxSize(startSize) {
81 buf = new hashnode<K, V> * [startSize]();
82 }
83
85 cleanup();
86 }
87
89 V get(const K& key) {
90
91 unsigned int index = hashFunc(key, maxSize);
92 auto entry = buf[index];
93
94 // loop through all of the buckets with the same hash until we found the right key.
95 while (entry != nullptr) {
96 if (entry->getKey() == key) {
97 return entry->getValue();
98 }
99 entry = entry->getNext();
100 }
101
102 // could not find item based on given key
103 throw no_item_found{};
104 }
105
107 void put(const K& key, const V& value) {
108
109 size++;
110
111 if (size >= maxSize) {
112 // rehash
113 rehash(maxSize + 8);
114 }
115
116 int index = hashFunc(key, maxSize);
117 hashnode<K, V>* prev = nullptr;
118 auto entry = buf[index];
119
120 // find an empty bucket that doenst have the same key.
121 while (entry != nullptr && entry->getKey() != key) {
122 prev = entry;
123 entry = entry->getNext();
124 }
125
126 if (entry == nullptr) {
127 entry = new hashnode<K, V>(key, value);
128 if (prev == nullptr) {
129 buf[index] = entry;
130 } else {
131 prev->setNext(entry);
132 }
133 } else {
134 // fallback
135 entry->setValue(value);
136 }
137 }
138
140 void remove(const K& key) {
141
142 // should we?
143 size--;
144
145 int index = hashFunc(key, maxSize);
146 hashnode<K, V>* prev = nullptr;
147 auto entry = buf[index];
148
149 // search for the right bucket with the correct key.
150 while(entry != nullptr && entry->getKey() != key) {
151 prev = entry;
152 entry = entry->getNext();
153 }
154
155 if (entry == nullptr) {
156 throw key_not_found{};
157 } else {
158 if (prev == nullptr) {
159 // remove the first bucket.
160 buf[index] = entry->getNext();
161 } else {
162 prev->setValue(entry->getNext());
163 }
164
165 delete entry;
166 }
167 }
168
170 void rehash(int newSize) {
171
172 //First create a new table with the desired size and everything to nullptr's
173 hashnode<K, V>** temp = new hashnode<K, V>*[newSize]{nullptr};
174
175 //Loop through all of the old items of the old table.
176 for (int i=0; i<maxSize; i++) {
177
178 auto oldEntry = buf[i];
179
180 // Check if this object is empty, if so we have to rehash the object and its buckets.
181 while (oldEntry != nullptr) {
182
183 // get the new hash
184 int index = hashFunc(oldEntry->getKey(), newSize);
185
186 auto newEntry = temp[index];
187
188 // If the new location is empty create a new one.
189 if (!newEntry) {
190 temp[index] = new hashnode<K, V>(oldEntry->getKey(), oldEntry->getValue());
191 } else {
192 //if the new location isnt empty search for an empty bucket.
193 auto prev = newEntry->getNext();
194
195 // get the last bucket
196 while (prev != nullptr) {
197 prev = prev->getNext();
198 }
199
200 // put our entry in that bucket
201 prev->setNext(new hashnode<K, V>(oldEntry->getKey(), oldEntry->getValue()));
202
203 }
204
205 // Get the next one to loop through all child buckets.
206 oldEntry = oldEntry->getNext();
207 }
208 }
209 //Delete the old buffer
210 cleanup();
211
212 // switch!
213 maxSize = newSize;
214 buf = temp;
215 }
216
217 private:
218
219 void cleanup() {
220 for (int i=0; i<maxSize; i++) {
221
222 // get the first bucket for the key / index.
223 auto entry = buf[i];
224
225 // loop through all off the buckets with the same key
226 while (entry != nullptr) {
227
228 auto prev = entry;
229
230 // set the entry to the next bucket of the same bucket.
231 entry = entry->getNext();
232
233 // delete this bucket
234 delete prev;
235 }
236
237 buf[i] = nullptr;
238 }
239
240 //destroy the allocated buffer;
241 delete[] buf;
242 }
243
244
245
246
247 F hashFunc;
248
249 hashnode<K, V>** buf; // just an array of pointers to hashnodes<K, V>
250 int size = 0;
251 // NOTE everytime the maxSize changes we have REHASH EVERYTHING!!
252 int maxSize = 0;
253
254 };
255
256}
257
258
259
260#endif //CATOS_HASHMAP_H
Definition application.h:13
Definition hashmap.h:11
const char * what()
Definition hashmap.h:12
Definition hashmap.h:17
const char * what()
Definition hashmap.h:18
Definition hashmap.h:27
hashnode * getNext() const
Definition hashmap.h:41
V getValue() const
Definition hashmap.h:37
void setValue(V newVal)
Definition hashmap.h:45
K getKey() const
Definition hashmap.h:33
void setNext(hashnode *newNext)
Definition hashmap.h:49
hashnode(const K &key, const V &value)
Definition hashmap.h:30
Definition hashmap.h:61
size_t operator()(const K &key, int Size) const
Definition hashmap.h:62
Definition hashmap.h:75
void rehash(int newSize)
Creates a new table of the given size and rehash all of the previous items.
Definition hashmap.h:170
~hashmap()
Definition hashmap.h:84
void remove(const K &key)
Removes the item.
Definition hashmap.h:140
V get(const K &key)
Gets the value based on the key given.
Definition hashmap.h:89
void put(const K &key, const V &value)
puts an item in the table.
Definition hashmap.h:107
hashmap(int startSize=8)
Basic constructor with a startSize of 8.
Definition hashmap.h:80