-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathhashset.c
361 lines (347 loc) · 7.33 KB
/
hashset.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdbool.h>
#include <ctype.h>
#define true 1
#define false 0
#define DEBUG if(0)
#define MAX_SIZE 10000
/*
1. ADD(S, k) = adiciona o int k ao conjunto S, retornando True se o int foi corretamente adicionado ou false se o int já pertencia ao conjunto.
2. DEL(S, k) = remove o int k do conjunto S, retornando True se o int foi corretamente removido ou False se o int não pertencia ao conjunto.
3. HAS(S, k) = retorna True se o int k pertence ao conjunto S ou false se o int não pertence ao conjunto.
*/
typedef struct _node
{
int data;
struct _node* next;
}node;
typedef struct _list
{
int size;
node* tail;
node* head;
}list;
typedef struct table
{
int base;
int numOfData[100]; //every index will be one table, the value of this array on the index will be the number of data written in it
list* tables[100];
}table;
int hashFunction(int value, int base)
{
return value%base;
}
list* initList()
{
list* new_list = (list*) malloc (sizeof(list));
new_list->head = NULL;
new_list->tail = NULL;
new_list->size = 0;
return new_list;
}
table* initTable(int base)
{
table* newTable = (table*) malloc(sizeof(table));
for (int i = 0; i < 100; i++)
{
newTable->tables[i] = initList();
newTable->numOfData[i] = 0;
}
newTable->base = base;
return newTable;
}
bool addListHead(list* lista, int value)
{
node* new_node = (node*) malloc(sizeof(node));
new_node->data = value;
if (lista->size == 0)
{
lista->head = new_node;
lista->tail = new_node;
lista->size++;
return true;
}
new_node->next = lista->head;
lista->head = new_node;
lista->size++;
return true;
}
bool addHashed(table* ht, int value, int key)
{
return addListHead(ht->tables[key],value);
}
bool DEL(table* S, int K,int key,int* comparCount)//remove
{
//DEBUG printf("deletando [%d]\t",K);
node* tmp = S->tables[key]->head;
while (tmp != NULL)
{
if(tmp->data == K){*comparCount += 1;return true;}
tmp = tmp->next;
*comparCount += 1;
}
return false;
}
bool HAS(table* S, int K, int* comparCount)//percente
{
//DEBUG printf("\ncheguei em HAS! \n");
int voltas = 0;
int key = hashFunction(K,S->base);
DEBUG printf("cheguei na chave [%d],base = [%d], k = [%d]\n",key,S->base,K);
node* tmp = S->tables[key]->head;
//if (tmp == NULL) DEBUG printf("CABEÇA NULA!\n");
while (tmp != NULL)
{
//DEBUG printf("oi\n");
if(tmp->data == K)
{
*comparCount += 1;
voltas++;
DEBUG printf("voltinhas [%d]\n",voltas);
return true;
}
*comparCount += 1;
voltas++;
//DEBUG printf("comparCount = [%d], voltas= [%d]\n",*comparCount,voltas);
tmp = tmp->next;
}
return false;
}
bool ADD(table* S, int K, int key, int* comparCount)
{
int ptr = 0;
if (!HAS(S,K, &ptr))
{
DEBUG printf("======================= ADICIONANDO ->\t chave[%d],base = [%d], k = [%d]\n",key,S->base,K);
addHashed(S,K,key);
*comparCount = ptr;
return true;
}
else
{
*comparCount = ptr;
return false;
}
}
int AtoI(char input[]) //returns an int from a string
{
int len = strlen(input)-3;
char *ptr = input+3; //creates a auxiliary ptr to transverse the string
int ans;
while (*ptr) {
if (isdigit(*ptr)) { //if string + x is digit
long val = strtol(ptr, &ptr, 10); //transforms the characters from string into base10 ints.
//DEBUG printf("%ld\n", val);
ans = val;
} else {
ptr++;
}
}
return ans;
}
int biggest(table* ht)
{
int max = 0;
for (int i = 0; i < 100; i++)
{
if(ht->numOfData[i]> max) max = ht->numOfData[i];
}
}
table* rehash(table* ht, int numCount)
{
int ptr = 0;
int new_base = 2*(ht->base)-1;
table* new_table = initTable(new_base);
if (numCount/ht->base >= 0.75)
{
DEBUG printf("%d/%d = %d\n",numCount,ht->base,numCount/ht->base);
DEBUG printf("\n!!!!REHASH?!?!?!?\n");
for (int i = 0; i < ht->base; i++)
{
node* tmp = ht->tables[i]->head;
while (tmp != NULL)
{
int oldkey, value, newkey;
oldkey = i;
value = tmp->data;
DEBUG printf("fazendo rehash de [%d]\t",value);
newkey = hashFunction(value,new_base);
ADD(new_table,value,newkey,&ptr);
tmp = tmp->next;
}
}
free(ht);
return new_table;
}
else
{
return ht;
}
}
int main()
{
int stepCount = 0;
int numCount = 0;
int base = 7;
int key;
int res;
int lenghtOfTable = 7;
char input[300];
int comparCount = 0;
table* ht = initTable(base);
while (gets(input))
{
long buffer;
switch (input[2])
{
case 'D'://add
buffer = AtoI(input);
key = hashFunction(buffer,base);
comparCount = 0;
//DEBUG printf("ADICIONANDO [%d]\n",buffer);
res = ADD(ht,buffer,key,&comparCount);
numCount++;
ht = rehash(ht,numCount);
//DEBUG printf("PASSOU! -: [%s]\n",input);
printf("%d ",stepCount);
printf("%d ",res);
printf("%d\n",comparCount);
break;
case 'S'://has
buffer = AtoI(input);
key = hashFunction(buffer,base);
comparCount = 0;
res = HAS(ht,buffer,&comparCount);
printf("%d ",stepCount);
//DEBUG printf("HAS [%d] ",buffer);
printf("%d ",res);
printf("%d\n",comparCount);
break;
case 'L'://del
buffer = AtoI(input);
key = hashFunction(buffer,base);
comparCount = 0;
//DEBUG printf("DELETANDO [%d],key[%d]\n",buffer,key);
res = DEL(ht,buffer,key,&comparCount);
printf("%d ",stepCount);
printf("%d ",res);
printf("%d\n",comparCount);
numCount--;
break;
case 'T'://prt
//DEBUG printf("PRT");
printf("%d ",stepCount);
printf("%d ",ht->base);
printf("%d ",numCount);
printf("%d\n",biggest(ht));
break;
}
memset(input,0,strlen(input));
stepCount++;
}
}
/*
ADD 61145465456215
HAS 68
ADD 99
ADD 51
HAS 61
HAS 3
DEL 99
ADD 90
HAS 42
ADD 94
ADD 51
ADD 70
ADD 59
ADD 80
HAS 59
ADD 35
ADD 3
PRT
HAS 94
DEL 70
DEL 34
DEL 84
HAS 53
HAS 97
ADD 65
ADD 79
ADD 66
ADD 64
HAS 64
HAS 15
DEL 65
ADD 82
ADD 68
ADD 77
ADD 22
ADD 2
DEL 81
HAS 55
HAS 1
HAS 85
DEL 51
ADD 70
HAS 35
PRT
HAS 90
ADD 43
PRT
ADD 70
HAS 92
ADD 58
DEL 61
PRT
ADD 95
HAS 100
HAS 10
DEL 76
HAS 64
ADD 41
PRT
HAS 90
HAS 84
HAS 58
DEL 43
ADD 68
HAS 80
HAS 30
PRT
PRT
ADD 71
PRT
HAS 2
DEL 66
HAS 70
ADD 30
ADD 70
ADD 30
DEL 98
HAS 35
ADD 7
ADD 62
HAS 30
HAS 68
ADD 73
DEL 68
HAS 27
ADD 50
HAS 7
ADD 47
HAS 90
ADD 21
PRT
HAS 35
DEL 77
ADD 0
DEL 70
HAS 79
HAS 95
HAS 50
HAS 71
PRT
*/
//TODO quando chega na linha 13, e na linha 15, parece que nao há adição de 59