哈希函数:对数据取模p
冲突处理方法:线性探测法
codeblocks 17 通过
// EasyHash @ChenYe 2018/12/02
#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#define ElemType int
using namespace std;
typedef struct
{
ElemType *data; //定义关键字为整型
int count; // 当前哈希表中的关键字个数
int length; // 当前哈希表的容量
}HashTable;
HashTable H;
int p; // 构造hash函数mod值
int Hash(ElemType key) // hash函数
{
return key%p;
}
int Collision(int p, int c) //冲突处理函数
{//以线性探测再散列作为冲突处理方式
// 冲突地址p, 增量地址c
return (p+c)%H.length; //重新找到的哈希地址
}
int SearchHash(HashTable H, ElemType key, int &p, int &c)
{//查找关键字key在哈希表中的位置,如果查找成功则返回SUCCESS 1
//用p返回关键字在哈希表中的位置。否则返回UNSUCCESS 0
//用p返回关键字要插入的位置,c为处理冲突的次数
int q;
p=q=Hash(key);//取得关键字的哈希地址
while(H.data[p]!=0&&H.data[p]!=key)
p=Collision(q,++c);//若该存储位置上已有关键字并且关键字值与key不相等
//则进行冲突处理
if(H.data[p]==key)
return 1;
else
return 0;
}
int InsertHash(HashTable &H, ElemType key)
{//若哈希表H中无关键字key则插入之
int c = 0, p;
if(SearchHash(H,key,p,c)) // 已经存在key
return -1;
if(c<H.length/2)
{
printf("哈希地址为%d \n",p);
H.data[p]=key;
H.count++;
printf("冲突次数为%d \n",c);
return 1;
}
else
{
printf("冲突次数过多,请定义合适的哈希函数!\n");
return -1;
}
}
void DisplayHashTable()
{
for(int i=0; i<H.length; i++) // 输出hash表
{
cout<<"第"<<i+1<<"个data:";
cout<<H.data[i]<<" \n";
}
}
int SearchHashTable(HashTable &H, ElemType key)
{// 查找hash表中key 存在则返回其位置,不存在则返回-1
int pos = Hash(key);
for(; pos<H.length; pos++)
{
if(H.data[pos] == key)
return pos+1;
}
if(pos == H.length)
return -1; // 未找到
}
void CreateHashTable()
{
int i;
ElemType key;
cout<<"输入hash表长度H.length=";
cin>>H.length;
cout<<"输入hash表mod值p=";
cin>>p;
H.data = (ElemType *)malloc(H.length*sizeof(ElemType)); // 申请空间
for(i=0; i<H.length; i++) // 初始化hash表
{
H.data[i] = 0;
}
cout<<"逐个输入创建hash表:"<<endl;
for(i=0; i<p; i++) // 逐个输入创建hash表
{
cin>>key;
InsertHash(H,key);
}
}
int main()
{
ElemType key;
CreateHashTable();
DisplayHashTable();
cout<<"search key in hash table\n now input key = ";
cin>>key;
int pos;
pos = SearchHashTable(H,key);
cout<<"the key in postion "<<pos;
return 0;
}
/*
test data:
20
13
19 14 23 1 68 20 84 27 55 11 10 79 0
55
*/