1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <stdbool.h>
4
5 typedef int ElementType;
6
7 struct SCHashListNode
8 {
9 ElementType Element;
10 int ExistNum;
11 struct SCHashListNode *Next;
12 };
13
14 struct SCHashTable
15 {
16 int TableSize;
17 struct SCHashListNode **SCHashNodeList;
18 };
19
20 bool _isPrime(int Input)
21 {
22 if (Input == 2 || Input == 3)
23 {
24 return true;
25 }
26 if (Input % 6 != 1 && Input % 6 != 5)
27 {
28 return false;
29 }
30 int i;
31 for (i = 5; i*i <= Input; i += 6)
32 {
33 if (Input % i == 0 || Input % (i+2) == 0)
34 {
35 return false;
36 }
37 }
38 return true;
39 }
40
41 int NextPrime(int Input)
42 {
43 bool state = _isPrime(Input);
44 while(!state)
45 {
46 state = _isPrime(++Input);
47 }
48 return Input;
49 }
50
51 int Hash(ElementType Key,int TSize)
52 {
53 return Key % TSize;
54 }
55
56 struct SCHashTable* SCHashTableInit(int TableSizeInput)
57 {
58 struct SCHashTable *HashTable;
59 int i;
60
61 HashTable = malloc(sizeof(struct SCHashTable));
62 HashTable -> TableSize = NextPrime(TableSizeInput);
63
64 HashTable->SCHashNodeList = malloc(HashTable -> TableSize*sizeof(struct SCHashListNode));
65
66 for(i = 0;i < HashTable -> TableSize;i ++)
67 {
68 HashTable->SCHashNodeList[i] = malloc(sizeof(struct SCHashListNode));
69 HashTable->SCHashNodeList[i]->Next = NULL;
70 HashTable->SCHashNodeList[i]->ExistNum = 0;
71 }
72 return HashTable;
73 }
74
75 void SCHashTableDelete(struct SCHashTable* HashTable)
76 {
77 struct SCHashListNode *PtrToList;
78
79 int i;
80 for(i = 0;i < HashTable->TableSize;i ++)
81 {
82 PtrToList = HashTable->SCHashNodeList[i];
83 free(PtrToList);
84 }
85 free(HashTable);
86 }
87
88 //if doesn't find,return NULL
89 struct SCHashListNode* SCHashListNodeFind(struct SCHashTable* HashTable,ElementType ToBeFind)
90 {
91 struct SCHashListNode *PtrToListNode;
92 struct SCHashListNode *PtrToList;
93
94 PtrToList = HashTable->SCHashNodeList[Hash(ToBeFind,HashTable->TableSize)];
95 PtrToListNode = PtrToList -> Next;
96
97 //probably need overload operator '='
98 while(PtrToListNode!=NULL && PtrToListNode->Element != ToBeFind)
99 {
100 PtrToListNode = PtrToListNode -> Next;
101 }
102 return PtrToListNode;
103 }
104
105 //if doesn't find,return NULL
106 struct SCHashListNode* _SCHashListNodeFindPre(struct SCHashTable* HashTable,ElementType ToBeFind)
107 {
108 struct SCHashListNode *PtrToListNode;
109 struct SCHashListNode *PtrToList;
110
111 PtrToList = HashTable->SCHashNodeList[Hash(ToBeFind,HashTable->TableSize)];
112 PtrToListNode = PtrToList;
113
114 //probably need overload operator '='
115 while(PtrToListNode->Next != NULL && PtrToListNode->Next->Element != ToBeFind)
116 {
117 PtrToListNode = PtrToListNode -> Next;
118 }
119 return PtrToListNode;
120 }
121
122 void SCHashListNodeInsert(struct SCHashTable* HashTable,ElementType ToBeInsert)
123 {
124 struct SCHashListNode *NewCell;
125 struct SCHashListNode *InsertPos;
126 struct SCHashListNode *PtrToList;
127
128 InsertPos = SCHashListNodeFind(HashTable,ToBeInsert);
129 if(InsertPos==NULL)//not find
130 {
131 NewCell = malloc(sizeof(struct SCHashListNode));
132
133 PtrToList = HashTable->SCHashNodeList[Hash(ToBeInsert,HashTable->TableSize)];
134 NewCell -> Next = PtrToList -> Next;
135 //probably need overload operator '='
136 NewCell -> Element = ToBeInsert;
137 NewCell -> ExistNum ++;
138 PtrToList -> Next = NewCell;
139 }
140 else
141 {
142 InsertPos->ExistNum ++;
143 }
144 }
145
146 //return the ExistNum,if not find return -1,if error return -2
147 int SCHashListNodeDelete(struct SCHashTable* HashTable,ElementType ToBeDelete)
148 {
149 struct SCHashListNode *DeletePosPre;
150 struct SCHashListNode *PtrToList;
151
152 DeletePosPre = _SCHashListNodeFindPre(HashTable,ToBeDelete);
153 if(DeletePosPre->Next==NULL)//not find
154 {
155 return -1;
156 }
157 else
158 {
159 if(DeletePosPre->Next->ExistNum==1)
160 {
161 struct SCHashListNode* TmpCell;
162 TmpCell = DeletePosPre->Next;
163 DeletePosPre->Next = DeletePosPre->Next->Next;
164 free(TmpCell);
165
166 return 0;
167 }
168 else
169 {
170 DeletePosPre->Next->ExistNum --;
171
172 return DeletePosPre->Next->ExistNum;
173 }
174 }
175 return -2;
176 }
177
178 int main()
179 {
180 struct SCHashTable* HashTable = SCHashTableInit(10000);
181 SCHashListNodeInsert(HashTable,23);
182 SCHashListNodeInsert(HashTable,23);
183 SCHashListNodeInsert(HashTable,23);
184 SCHashListNodeDelete(HashTable,23);
185 SCHashListNodeInsert(HashTable,47);
186 SCHashListNodeInsert(HashTable,50);
187 struct SCHashListNode *OutputNode = SCHashListNodeFind(HashTable,23);
188 printf("%d %d\n",OutputNode->Element,OutputNode->ExistNum);
189 OutputNode = SCHashListNodeFind(HashTable,47);
190 printf("%d %d\n",OutputNode->Element,OutputNode->ExistNum);
191 OutputNode = SCHashListNodeFind(HashTable,39);
192 if(OutputNode == NULL)
193 printf("where is my princess Hatsune Miku?\n");
194 SCHashTableDelete(HashTable);
195 return 0;
196 }