哈希函数与哈希表

哈希函数和哈希表

  RandomPool

 

 

 

RandomPool

设计RandomPool结构
【题目】 设计一种结构,在该结构中有如下三个功能:

insert(key):将某个key加入到该结构,做到不重复加入

delete(key):将原本在结构中的某个key移除

getRandom(): 等概率随机返回结构中的任何一个key。

【要求】 Insert、delete和getRandom方法的时间复杂度都是O(1)

 

思路:

因为时间复杂度需要为O(1),所以用两个哈希表来解决,一个哈希表是 key,index,另一个是 index,key

当 insert 的时候,先判断这个key是否在表中,如果不在表内就将两个表分别加入key的值,用size来计数,顺便做下标。

当 delete 的时候,先判断这个值是否存在,然后再进行一个 " 填洞 "操作。

 

可以通过上面的图来看到,现在是把 b 删除,然后用表内最后的值 ' d ' 来进行 " 填上 ",index的值不变,最后再把多余的最后一条记录删除掉,size 也减 1

最后等概率随机返回一个key值,就直接用系统自带的rand() 随机函数生成一个下标,然后用另一个哈希表返回 对应的值。

template<typename T>
class Pool
{
public:
    Pool()
    {
        int size = 0;
    }
    void insert(T key)
    {
        if (!keyIndexMap.count(key))
        {
            keyIndexMap.insert(make_pair(key, size));
            indexKeyMap.insert(make_pair(size++, key));
        }
    }
    void Delete(T key)
    {
        if (keyIndexMap.count(key))
        {
            int deleteIndex = keyIndexMap[key];
            int lastIndex = --size;
            T lastKey = indexKeyMap[lastIndex];
            keyIndexMap.insert(make_pair(lastKey, deleteIndex));
            indexKeyMap.insert(make_pair(deleteIndex, lastKey));
            keyIndexMap.erase(key);
            indexKeyMap.erase(lastIndex);
        }
    }
    T getRandom()
    {
        if (size == 0)
        {
            return NULL;
        }
        int randomIndex = (int)(rand() % size);
        return indexKeyMap[randomIndex];
    }

public:
    unordered_map<T, int>keyIndexMap;
    unordered_map<int, T>indexKeyMap;
    int size;
};

 

 

posted @ 2020-09-02 08:22  袁君(Louis)  阅读(240)  评论(0)    收藏  举报