Lab Journal - 13 27122023 103335am
Lab Journal - 13 27122023 103335am
Objective(s):
Upon completion of this lab session, learners will be able to:
Implement the concept of hashing and has function.
Implement a scenario based on hashing.
Lab Tasks:
Task 1
Implement a simple hash table in C++ to store key-value pairs. The hash table should support the
following operations:
insert(key, value): Insert a key-value pair into the hash table. If the key already exists, update
the corresponding value.
get(key): Retrieve the value associated with the given key. If the key is not present, return a
default value (e.g., -1).
remove(key): Remove the key-value pair with the given key from the hash table.
The hash function should convert the key into an index for the hash table.
Resolve collisions using a suitable collision resolution technique (e.g., chaining or open
addressing).
Ensure the hash table dynamically resizes itself to maintain an appropriate load factor.
You can use standard C++ libraries for dynamic arrays or linked lists if needed.
Provide the implementation along with a brief explanation of your chosen hash function and collision
resolution strategy in comments. Additionally, include sample code demonstrating the usage of your
hash table with multiple insertions, retrievals, and removals.
#include <iostream>
// Find the key in the specified bucket and return the node
Node<K, V>* findInBucket(Node<K, V>* bucket, const K& key) const {
Node<K, V>* current = bucket;
while (current != nullptr && current->key != key) {
current = current->next;
}
return current;
}
// Resize the hash table when load factor exceeds the threshold
void resizeTable() {
if (static_cast<double>(size()) / tableSize > loadFactorThreshold) {
size_t newSize = tableSize * 2;
Node<K, V>** newTable = new Node<K, V>* [newSize]();
current->next = newTable[newIndex];
newTable[newIndex] = current;
current = temp;
}
}
delete[] table;
table = newTable;
tableSize = newSize;
}
}
public:
HashTable() : table(new Node<K, V>* [initialSize]()), tableSize(initialSize) {}
~HashTable() {
for (size_t i = 0; i < tableSize; ++i) {
Node<K, V>* current = table[i];
while (current != nullptr) {
Node<K, V>* temp = current;
current = current->next;
delete temp;
}
Page 2 of 7
%
Enrollment Number: ____________________________
}
delete[] table;
}
if (node != nullptr) {
// Key exists, update the value
node->value = value;
}
else {
// Key not found, insert a new key-value pair
Node<K, V>* newNode = new Node<K, V>(key, value);
newNode->next = bucket;
bucket = newNode;
resizeTable();
}
}
if (current != nullptr) {
if (prev != nullptr) {
prev->next = current->next;
}
else {
bucket = current->next;
}
delete current;
}
}
private:
size_t tableSize;
};
int main() {
HashTable<std::string, int> myHashTable;
// Retrieve values
cout << "Value for 'One': " << myHashTable.get("One") << endl;
cout << "Value for 'Four': " << myHashTable.get("Four") << endl;
// Remove a key
myHashTable.remove("Two");
return 0;
}
Page 4 of 7
%
Enrollment Number: ____________________________
Task 2
You are working on a system that manages user authentication for a web application. To improve
performance and security, you decide to implement a hashed password storage mechanism. Each
user's password will be hashed and stored in a hash table.
Design and implement a C++ program that utilizes hashing to store and verify user passwords. The
program should include the following functionalities:
1. User Registration:
Prompt the user to enter a username and password.
Hash the password and store the hashed password in a hash table.
Ensure that the program prevents duplicate usernames.
2. User Login:
Prompt the user to enter their username and password.
Retrieve the hashed password from the hash table based on the entered username.
Verify the entered password by comparing its hash with the stored hash.
Allow login if the verification is successful; otherwise, deny access.
3. Collision Handling:
Discuss how you would handle collisions in the hash table, especially in the context of storing
hashed passwords.
Include the complete C++ implementation of your program and provide a sample interaction
demonstrating the registration and login process. Additionally, explain how your implementation
addresses security concerns and collision handling.
#include <iostream>
#include <string>
#include <unordered_map>
class UserAuthentication {
private:
// Simple string hashing algorithm (for illustration purposes)
static size_t hashString(const std::string& str) {
size_t hash = 0;
for (char ch : str) {
hash = (hash * 31) + static_cast<size_t>(ch);
}
return hash;
}
public:
bool registerUser(const std::string& username, const std::string& password) {
// Check if the username already exists
size_t hashedUsername = hashString(username);
if (userTable.find(hashedUsername) != userTable.end()) {
std::cout << "Username already exists. Choose a different username.\n";
return false;
}
// Hash the entered password and compare with the stored hash
size_t hashedEnteredPassword = hashString(password);
size_t storedHashedPassword = std::stoull(userEntry->second);
if (hashedEnteredPassword == storedHashedPassword) {
std::cout << "Login successful.\n";
return true;
}
else {
std::cout << "Incorrect password. Login failed.\n";
return false;
}
}
};
int main() {
UserAuthentication userAuth;
// User Registration
userAuth.registerUser("user1", "password123");
// User Login
userAuth.loginUser("user1", "password123"); // Should succeed
userAuth.loginUser("user1", "wrongpassword"); // Should fail
return 0;
}
Page 6 of 7
%
Enrollment Number: ____________________________
Note : Attempt all tasks and get them checked by your Lab Instructor. Also for each task,
attach a screenshot of the output. You are free to use any other helping functions in your code.
Page 7 of 7