📌  相关文章
📜  ph vid - C++ (1)

📅  最后修改于: 2023-12-03 15:03:33.802000             🧑  作者: Mango

Introduction to PH VID in C++

What is PH VID?

PH VID is an abbreviation for Perfect Hashing with Variable Internal Division. It is a technique used in computer programming for creating a perfect hash function that can hash a set of keys with no collisions. The term “perfect” means that every key in the set has a unique hash value. This approach to hashing is faster and more efficient compared to other hashing techniques.

How does PH VID work?

PH VID uses two hash functions. The first function hashes the keys into a set of buckets. The second function hashes the keys within each bucket to a unique location. The size of the buckets can be determined based on the number of keys and the desired load factor.

The key feature of PH VID is that it uses variable internal division. This means that the size of each bucket can be adjusted to always be a power of two. This is important because when the size of the bucket is a power of two, then instead of dividing by the size of the bucket, a bitwise AND operation can be used. This operation is much faster than division.

To summarize, the steps for PH VID are as follows:

  1. Hash keys into a set of buckets using the first hash function.
  2. Determine the size of each bucket to be a power of two using variable internal division.
  3. Within each bucket, hash the keys using the second hash function to a unique location.
Implementation in C++

Here is an example implementation of PH VID in C++:

#include <iostream>
#include <vector>
#include <cmath>
#include <algorithm>

using namespace std;

template<typename T> class PerfectHash {
private:
    vector<T> keys;
    vector<pair<int,int> > hash_table;
    static int hash(int bucket_index, T key) {
        int hash_code = 0;
        while(key > 0) {
            hash_code ^= (key & (bucket_index-1));
            key /= bucket_index;
        }
        return hash_code;
    }
    static bool compare_pairs(const pair<int,int>& a, const pair<int,int>& b) {
        return a.second < b.second;
    }
public:
    PerfectHash(const vector<T> &keys) {
        this->keys = keys;
        int num_buckets = keys.size();
        int bucket_size = (int)ceil(log2(num_buckets));
        num_buckets = (int)pow(2, bucket_size);
        vector<int> bucket(num_buckets);
        for (int i = 0; i < keys.size(); ++i) {
            int index = hash(num_buckets, keys[i]);
            while(bucket[index] > 0) {
                num_buckets++;
                bucket.resize(num_buckets);
                index = hash(num_buckets, keys[i]);
            }
            bucket[index] = keys[i];
        }
        hash_table.resize(num_buckets);
        for(int i=0;i<num_buckets;i++) hash_table[i]={-1,i};
        for(int i=0;i<keys.size();i++){
            int index = hash(num_buckets, keys[i]);
            hash_table[index]={keys[i],i};
        }
        sort(hash_table.begin(),hash_table.end(),compare_pairs);
    }
    int operator[](T key) const {
        int index = hash(hash_table.size(), key);
        if(hash_table[index].first != key) return -1;
        return hash_table[index].second;
    }
};
Conclusion

PH VID is an efficient method for creating a perfect hash function. It uses variable internal division to create a hash function that is faster and more efficient than other hashing techniques. The implementation in C++ provided above can be used to create perfect hash functions for a set of keys without collisions.