前言
哈希表的查找方式作为查找比较快的一种,我们很有必要去了解一下他的基本原理
哈希表
定义:哈希表是根据关键码值直接进行数据访问的数据结构,它通过把关键码映射到一个位置来访问记录,这个映射函数叫哈希函数,存放记录的数组叫哈希表
最简单的哈希查找
当知道数据的范围为0~99时,使用哈希的思想就能很快的统计出来数据的个数
void hash_table (int table[],int arr[],int len)
{
for (int i=0;i<len;i++)
//这就是借助数组的下标统计数据出现的次数
table[arr[i]]++;
}
int main()
{
int table[100]={0};
int arr[]={1,11,43,23,22,44,1,1,1,3,4,5};
int len=sizeof(arr)/sizeof(arr[0]);
hash_table(table,arr,len);
for (int i=0;i<100;i++)
{
if (table[i]!=0)
printf("%d have %d\n",i,table[i]);
}
}
当数据范围很大的时候
当数据范围很大的时候,我们就需要使用到哈希算法来将数据转化为表长的下标,比如举几个最简单的例子,就是对字符串和较大数字的存储
char *table[100];//我们还是定义一个长度为100的指针数组
int hash_int(int val)
{
//通过取模对大数字进行运算
int ret=val%11;
return ret;
}
int hash_char(char *buf)
{
int len=0;
while (buf !=NULL)
{
len=len+*buf;
}
len =len%11;
return len;
}
但是这样的话,我们就可以发现一些问题,就是我们不同数字得到的哈希值可能相同,比如12,23,111,他们的哈希值都是1,这样就会导致大家也不知道这块数据存储的是哪个数,这就是哈希冲突
哈希冲突的解决方法
开放地址法
线性探测:使用数组的构造方法,如果冲突的话就放到下一个存储单元
平方探测:当发生冲突的时,将冲突的序列放到 d,d+1^2, d-1^2, d+2^2, d-2^2
拉链方法(链地址法)
将hash值相同的数据使用链表链接在一起
总结
其实使用哪一种冲突的解决方法,还是要根据数值的属性来决定,要保证评价查找长度的尽可能小