To write a custom hash function for your own data type, you need to specialize the std::hash
template for your type. Here's a step-by-step guide:
Step 1: Create your custom data type, for example, a Person
 struct:
#include <string>
struct Person {
std::string name;
int age;
};
Step 2: Specialize the std::hash
 template for your data type:
#include <utility>
#include <string>
namespace std {
template <>
struct hash<Person> {
size_t operator()(const Person& person) const {
// Combine the hash values of name and age
size_t nameHash =
std::hash<std::string>{}(person.name);
size_t ageHash =
std::hash<int>{}(person.age);
return nameHash ^ (ageHash << 1);
}
};
}
In the operator()
function, you define how to calculate the hash value for your data type. In this example, we combine the hash values of the name
and age
members using the XOR operator (^
) and left shift (<<
).
Step 3: Ensure that your data type has a proper equality comparison operator (operator==
):
bool operator==(const Person& lhs,
const Person& rhs) {
return lhs.name == rhs.name
&& lhs.age == rhs.age;
}
This is necessary because hash tables use equality comparison to resolve collisions.
Now you can use your custom data type with hash-based containers like std::unordered_set
or std::unordered_map
:
#include <utility>
#include <string>
#include <iostream>
#include <unordered_set>
struct Person {/*...*/}
bool operator==(Person, Person) {/*...*/}
namespace std {/*...*/}
int main() {
std::unordered_set<Person> people;
people.insert({"John", 30});
people.insert({"Alice", 25});
for (const auto& person : people) {
std::cout << person.name << " - "
<< person.age << '\n';
}
}
John - 30
Alice - 25
Remember, a good hash function should distribute the hash values uniformly across the range of possible values to minimize collisions and maintain the efficiency of hash-based containers.
Answers to questions are automatically generated and may not have been reviewed.
std::hash
This lesson provides an in-depth look at hashing in C++, including std::hash
, collision strategies, and usage in hash-based containers.