Files
2026-03-05 13:39:39 +01:00

293 lines
8.7 KiB
C++

//##################################################################
// PROGRAMMERINGSUPPGIFT 3
// DATASTRUKTURER OCH ALGORITMER
// HASH TABELL
//==================================================================
// HASH.HPP
// Filen innehåller hashfunktionerna
// Christian Ohlsson
// Ingela Johansson
// Anna-Maria Haglund
// Karlstad 981007
//==================================================================
#include "header.hpp"
//##################################################################
//Function: hashClass()
//Task: constuctorn
//Calls: nothing
//==================================================================
hashClass::hashClass()
{
prime();
PRIMENUMBER=0;
ARRAYSIZE = DEFAULTSIZE;
hashPtr = new hashNode[ARRAYSIZE];
for(int i=0; i<ARRAYSIZE ; i++) {
strcpy(hashPtr[i].name, "");
strcpy(hashPtr[i].number, "");
hashPtr[i].exist = FALSE;
}
}
//##################################################################
//Function: ~hashclass
//Task: destructorn
//Calls: nothing
//==================================================================
hashClass::~hashClass(){ delete hashPtr; }
//##################################################################
//Function: getSize()
//Task: returnerar storleken på hashtabellen
//Calls: nothing
//==================================================================
int hashClass::getSize(){ return ARRAYSIZE; }
//##################################################################
//Function: nextPrime()
//Task: returnerar nästa primtal
//Calls: nothing
//==================================================================
int hashClass::nextPrime()
{
PRIMENUMBER++;
return primeArray[DEFAULTPRIMENUMBER+PRIMENUMBER];
}
//##################################################################
//Function: prime()
//Task: lägger in primtalen i en array
//Calls: isPrime()
//==================================================================
void hashClass::prime()
{
int i = 1, num=FIRSTPRIME;
primeArray[0] = STARTPRIME;
while(i<PRIMEARRAYSIZE) {
if(isPrime(num, i, primeArray)) {
primeArray[i] = num;
i++;
}
num = (num+PRIMESTEP);
}
}
//##################################################################
//Function: isPrime()
//Task: kollar om ett tal är ett primtal
//Calls: nothing
//=================================================================
bool hashClass::isPrime(int nummer, int antal, int primeArray[PRIMEARRAYSIZE])
{
for(int i = 0; i < antal; i++)
if(nummer%primeArray[i] == 0)
return FALSE;
return TRUE;
}
//##################################################################
//Function: search()
//Task: söker efter ett namn i tabellen
//Calls: hash1() och hash2()
//==================================================================
bool hashClass::search(nameType name)
{
int location = hash1(name);
if(strcmp(hashPtr[location].name, name) == 0)
return TRUE;
else
while(hashPtr[location].exist == TRUE) {
location = location + hash2(hash1(name));
if(location > ARRAYSIZE)
location = location - ARRAYSIZE;
if(strcmp(hashPtr[location].name, name) == 0)
return TRUE;
}
return FALSE;
}
//##################################################################
//Function: getNode()
//Task: hämtar en nod ur tabellen, d.v.s. namn telefonnummer och
// "deleted-flaggan"
//Calls: hash1() och hash2()
//==================================================================
hashNode hashClass::getNode(nameType &oneName)
{
int location = hash1(oneName);
if(strcmp(hashPtr[location].name, oneName) == 0)
return (hashPtr[location]);
else
do {
location = location + hash2(hash1(oneName));
if(location>ARRAYSIZE) {
location = (location-ARRAYSIZE);
if(strcmp(hashPtr[location].name, oneName) == 0)
return hashPtr[location];
}
}while(hashPtr[location].exist == FALSE);
}
//##################################################################
//Function: biggerHash()
//Task: kollar om en större tabell behövs (om 80% av positionerna
// är upptagna)
//Calls: checkOccupied()
//==================================================================
bool hashClass::biggerHash()
{
float siz = INSERTFACTOR*getSize();
int occ = checkOccupied();
if(occ>=siz)
return TRUE;
return FALSE;
}
//##################################################################
//Function: newHashArray()
//Task:
//Calls: reHash()
//==================================================================
void hashClass::newHashArray()
{
int oldSize = ARRAYSIZE;
ARRAYSIZE = nextPrime();
reHash(oldSize);
}
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
bool hashClass::anotherHash()
{
int del=0;
float siz = DELETEFACTOR*getSize();
for(int i=0; i<ARRAYSIZE ; i++)
if(hashPtr[i].exist == TRUE && !hashPtr[i].name[0])
del++;
if(del>=siz)
return TRUE;
return FALSE;
}
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
void hashClass::reHash(int oldSize)
{
int location;
hashNode *tempPtr = new hashNode[ARRAYSIZE];
for(int j=0; j<oldSize ; j++) {
strcpy(tempPtr[j].name, hashPtr[j].name);
strcpy(tempPtr[j].number, hashPtr[j].number);
tempPtr[j].exist = hashPtr[j].exist;
}
destroyHash(oldSize);
hashPtr = new hashNode[ARRAYSIZE];
for(int k=0; k<ARRAYSIZE ; k++) {
strcpy(hashPtr[k].name, "");
strcpy(hashPtr[k].number, "");
hashPtr[k].exist = FALSE;
}
for(int i=0; i<oldSize ; i++)
if(tempPtr[i].exist == TRUE && tempPtr[i].name[0]) {
location = hash1(tempPtr[i].name);
if(hashPtr[location].exist == FALSE)
insert(location, tempPtr[i]);
else
while(hashPtr[location].exist == TRUE) {
location = location + hash2(hash1(tempPtr[i].name));
if(location > ARRAYSIZE)
location = location - ARRAYSIZE;
if(hashPtr[location].exist == FALSE)
insert(location, tempPtr[i]);
}
}
delete tempPtr;
}
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
int hashClass::hash1(nameType name)
{
int sum = 0;
for(int i=0 ; i<strlen(name) ; i++)
sum = name[i] + sum;
return (sum % ARRAYSIZE);
}
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
int hashClass::hash2(int key){ return(STEPSIZE - (key % STEPSIZE)) }
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
int hashClass::checkOccupied()
{
int occupied = 0;
for(int i=0 ; i<ARRAYSIZE ; i++)
if(hashPtr[i].exist == TRUE)
occupied++;
return occupied;
}
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
void hashClass::destroyHash(int oldSize)
{
for(int i = 0; i < oldSize; i++)
delHash(i);
}
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
void hashClass::del(int location)
{
strcpy(hashPtr[location].name, "");
strcpy(hashPtr[location].number, "");
hashPtr[location].exist = TRUE;
}
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
void hashClass::delHash(int location)
{
strcpy(hashPtr[location].name, "");
strcpy(hashPtr[location].number, "");
hashPtr[location].exist = FALSE;
}
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
void hashClass::insert(int location, hashNode &newNode)
{
strcpy(hashPtr[location].name, newNode.name);
strcpy(hashPtr[location].number, newNode.number);
hashPtr[location].exist = TRUE;
}
//##################################################################
//Function:
//Task:
//Calls:
//==================================================================
void hashClass::save(fstream &fil)
{
int i = 0;
while(i < ARRAYSIZE) {
if((hashPtr[i].name[0]) && (hashPtr[i].exist == TRUE))
fil.write((char*)& hashPtr[i],sizeof(hashPtr[i]));
i++;
}
}