#pragma once
#include<iostream>
#include<string>
using namespace std;
enum Status
{
EMPTY, //为空
EXIST, //存在pair
DELETED, //存在过pair,但是被删除了
};
//一个算法将字符串转化为整数
static size_t BKDRHash(const char * str)
{
unsigned int seed = 131; // 31 131 1313 13131 131313
unsigned int hash = 0;
while (*str)
{
hash = hash * seed + (*str++);
}
return (hash & 0x7FFFFFFF);
}
//为string定制的仿函数
struct __HashFuncS
{
size_t operator()(const string& str)
{
return BKDRHash(str.c_str());
}
};
//对 int型
struct __HashFuncInt
{
size_t operator()(const int& key)
{
return key;
}
};
//这里用的是除留余数法构建哈希表,并用开放地址法-二次探测 处理哈希冲突,载荷因子限制为0.7
template <class K, class V, class _HashFunc = __HashFuncInt >
class HashTables
{
static const size_t InitialCapacity = 10;
public:
HashTables(size_t capacity = InitialCapacity)
: _status(new Status[capacity])
, _tables(new pair<K, V>[capacity])
, _size(0)
, _capacity(capacity)
{
for (size_t i = 0; i < capacity; ++i)
{
_status[i] = EMPTY;
}
}
void CheckCapacity()
{
if (_size * 10 / _capacity == 7)
{
size_t newcapacity = 2 * _capacity;
HashTables ht(newcapacity);
size_t i = 0;
for (; i < _capacity; ++i)
{
if (_status[i] == EXIST)
ht.Insert(_tables[i].first, _tables[i].second);
}
swap(_tables, ht._tables);
swap(_status ,ht._status);
swap(_size, ht._size);
swap(_capacity, ht._capacity);
}
}
pair<K, V>* Find(const K& key)
{
size_t i = 0;
size_t index = HashFunc(key, i);
while (_status[index]!= EMPTY)
{
if (_tables[index].first == key)
{
return &_tables[index];
}
index = HashFunc(key, ++i);
}
return NULL;
}
bool Insert(const K& key,const V& value)
{
if (Find(key))
return false;
CheckCapacity();
size_t i = 0;
size_t index = HashFunc(key, i);
while (_status[index]==EXIST)
{
index = HashFunc(key, ++i);
}
_tables[index].first = key;
_tables[index].second = value;
_status[index] = EXIST;
_size++;
return true;
}
void print()
{
for (size_t i = 0; i < _capacity; ++i)
{
if (_status[i] == EXIST)
{
cout <<i<< " key: " << _tables[i].first << " value: " << _tables[i].second << endl;
}
else
{
cout << i << " no" << endl;
}
}
}
private:
size_t HashFunc(const K& key, size_t i)
{
return (_HashFunc()(key) + i*i) % _capacity;
}
protected:
Status* _status;
pair<K, V>* _tables;
size_t _size;
size_t _capacity;
};
下面给一个测试用例:
#include"hashtable.h"
void test1()
{
HashTables<int, int> ht;
int a[] = { 89, 18, 49, 58, 9 };
for (size_t i = 0; i < sizeof(a) / sizeof(int); ++i)
{
ht.Insert(a[i], i);
}
ht.print();
}
void test2()
{
HashTables<string,string,__HashFuncS> ht2;
ht2.Insert("sort", "排序");
ht2.Insert("sort1", "排序1");
ht2.Insert("sort2", "排序2");
ht2.Insert("sort3", "排序3");
ht2.print();
}
int main()
{
test2();
system("pause");
return 0;
}