hash表-平方探测,数据结构与算法分析第四版的(增加了上文的nextPrime)

来源:互联网 发布:毫州康美中药城淘宝店 编辑:程序博客网 时间:2024/05/29 19:55
/*************************************************************************> File Name: HashTable2.h> Author:keson> Mail:keson@bupt.edu.cn> Created Time: 2014年11月26日 星期三 11时05分23秒 ************************************************************************/#include<iostream>#include<vector>#include<string>using namespace std;class hashValue{    public:    size_t operator()(const string &key)    {            size_t hashVal=0;            for(auto c:key)               hashVal=37*hashVal+c;            return hashVal;        }};template<typename HashedObj>class HashTable2{public:    explicit HashTable2(int size=101):array(nextPrime(size))    {makeEmpty();}    bool contains(const HashedObj &x) const    {        return isActive(findPos(x));    }    void makeEmpty()    {        currentSize=0;        for(auto &entry:array)          entry.info=EMPTY;    }    bool insert(const HashedObj &x)    {        int currentPos=findPos(x);        if(isActive(currentPos))           return false;        array[currentPos].element=x;        array[currentPos].info=ACTIVE;        if(++currentSize>array.size()/2)          rehash();        return true;    }    bool insert(HashedObj &&x)    {        int currentPos=findPos(x);        if(isActive(currentPos))           return false;        array[currentPos].element=std::move(x);        array[currentPos].info=ACTIVE;        if(++currentSize>array.size()/2)          rehash();        return true;    }    bool remove(const HashedObj &x)    {        int currentPos=findPos(x);        if(!isActive(currentPos))           return false;        array[currentPos].info=DELETED;        return true;    }    enum EntryType{ACTIVE,EMPTY,DELETED};    void print()    {        for(auto entry:array)          if(entry.info==ACTIVE)            cout<<entry.element<<endl;    }private:    struct HashEntry    {        HashedObj element;        EntryType info;        HashEntry(const HashedObj &e=HashedObj{},EntryType i=EMPTY)        :element{e},info{i} {}        HashEntry(HashedObj &&e,EntryType i=EMPTY)        :element{std::move(e)},info{i} {}    };    vector<HashEntry> array;    int currentSize;    bool isActive(int currentPos) const    {        return array[currentPos].info==ACTIVE;    }    int findPos(const HashedObj &x) const    {        int offset=1;        int currentPos=myhash(x);        //the order can't change.        while(array[currentPos].info!=EMPTY&&              array[currentPos].element!=x)        {            currentPos+=offset;  //Compute ith probe            offset+=2;            if(currentPos>=array.size())              currentPos-=array.size();        }        return currentPos;    }   bool isPrime(int num)   {     if (num == 2 || num == 3)     {        return true;     }     if (num % 6 != 1 && num % 6 != 5)     {        return false;     }     for (int i = 5; i*i <= num; i += 6)     {        if (num % i == 0 || num % (i+2) == 0)        {            return false;        }     }       return true;    }   int nextPrime(int n)   {     bool state=isPrime(n);     while(!state)      {        state=isPrime(++n);      }      return n;    }    void rehash()    {        vector<HashEntry> oldArray=array;        //Create new double-sized,empty table        array.resize(nextPrime(2*oldArray.size()));        for(int j=0;j<array.size();j++)          array[j].info=EMPTY;        currentSize=0;        for(int i=0;i<oldArray.size();i++)           if(oldArray[i].info==ACTIVE)             insert(oldArray[i].element);    }    size_t myhash(const HashedObj &x) const    {        static    hashValue hf;        return hf(x)%array.size();    }};int main(){    HashTable2<string> a;    a.insert("Hello");    a.print();}

0 0
原创粉丝点击