码迷,mamicode.com
首页 > 其他好文 > 详细

hash表简单实现

时间:2017-03-30 11:35:55      阅读:203      评论:0      收藏:0      [点我收藏+]

标签:log   大小   href   拉链法   rod   分类   div   csdn   简便   

查找算法大总结: http://www.cnblogs.com/maybe2030/p/4715035.html#_label6

常用的hash函数: http://blog.csdn.net/mycomputerxiaomei/article/details/7641221

什么是哈希表(Hash)?

  我们使用一个下标范围比较大的数组来存储元素。可以设计一个函数(哈希函数, 也叫做散列函数),使得每个元素的关键字都与一个函数值(即数组下标)相对应,于是用这个数组单元来存储这个元素;也可以简单的理解为,按照关键字为每一个元素"分类",然后将这个元素存储在相应"类"所对应的地方。但是,不能够保证每个元素的关键字与函数值是一一对应的,因此极有可能出现对于不同的元素,却计算出了相同的函数值,这样就产生了"冲突",换句话说,就是把不同的元素分在了相同的"类"之中。后面我们将看到一种解决"冲突"的简便做法。
  总的来说,"直接定址"与"解决冲突"是哈希表的两大特点。

  什么是哈希函数?

  哈希函数的规则是:通过某种转换关系,使关键字适度的分散到指定大小的的顺序结构中,越分散,则以后查找的时间复杂度越小,空间复杂度越高。

  算法思想:哈希的思路很简单,如果所有的键都是整数,那么就可以使用一个简单的无序数组来实现:将键作为索引,值即为其对应的值,这样就可以快速访问任意键的值。这是对于简单的键的情况,我们将其扩展到可以处理更加复杂的类型的键。

  算法流程:

  1)用给定的哈希函数构造哈希表;
  2)根据选择的冲突处理方法解决地址冲突;
    常见的解决冲突的方法:拉链法和线性探测法。详细的介绍可以参见:浅谈算法和数据结构: 十一 哈希表
  3)在哈希表的基础上执行哈希查找。
  哈希表是一个在时间和空间上做出权衡的经典例子。如果没有内存限制,那么可以直接将键作为数组的索引。那么所有的查找时间复杂度为O(1);如果没有时间限制,那么我们可以使用无序数组并进行顺序查找,这样只需要很少的内存。哈希表使用了适度的时间和空间来在这两个极端之间找到了平衡。只需要调整哈希函数算法即可在时间和空间上做出取舍。

 

实现:

定义hash:

 1 typedef struct node
 2 {
 3     int value;
 4     struct node *next;
 5 }NODE; 
 6 
 7 typedef struct hash
 8 {
 9     int size;
10     NODE **list;
11 }HASH;

初始化hash:

 1 HASH *HashInit(int size)
 2 {
 3     if (size <= 0)
 4         return NULL;
 5     HASH *hash = (HASH*)malloc(sizeof(HASH));
 6     if (NULL == hash)
 7         return NULL;
 8     hash->size = size;
 9     hash->list = (NODE**)malloc(sizeof(NODE*) * hash->size);
10     if (NULL == hash->list)
11     {
12         free(hash);
13         hash = NULL;
14         return NULL;
15     }
16     int i;
17     for (i = 0; i < size; i++)
18     {
19         hash->list[i] = (NODE*)malloc(sizeof(NODE));
20         hash->list[i]->next = NULL;
21     }
22     return hash;
23 }

 

hash查找:

NODE *HashFind(HASH *hash, int key)
{
    NODE *list = hash->list[HashFun(key, hash->size)];
    NODE *node = list->next;
    for (;NULL != node && node->value != key; node = node->next);
    return node;
}

hash插入:

void HashInstert(HASH* hash, int key)
{
    if (NULL != HashFind(hash, key))
        return;
    NODE *node = (NODE*)malloc(sizeof(NODE));
    if (NULL == node)
        return;
    NODE *list = hash->list[HashFun(key, hash->size)];
    node->value = key;
    node->next = list->next;
    list->next = node;
}

 

hash表简单实现

标签:log   大小   href   拉链法   rod   分类   div   csdn   简便   

原文地址:http://www.cnblogs.com/dapaitou2006/p/6644921.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!