转自:http://t.zoukankan.com/lizhanwu-p-4303410.html
1.拉链法代码实现
所想插入的类型:
char* names[]={"First Name","Last Name","address","phone","k101","k110"}; char* descs[]={"Kobe","Bryant","USA","26300788","Value1","Value2"}; for(int i=0; i < 6; ++i) insert(names[i], descs[i]);
桶中节点类型定义:
typedef struct node{ char *name;//字段名 char *desc;//描述 struct node *next; }node;
插入函数:
static node* hashtable[HASHSIZE];//定义一个哈希数组,每个值表示存放的桶的头结点指针,每个桶都会形成一个链表 int insert(char* name, char* desc) { unsigned int hashvalue; hashvalue = hash(name);//首先通过哈希函数获取到地址,即所在的桶 //头插法,不管该hash位置有没有其他结点,直接插入结点 node* np = malloc_node(name, desc); if (np == NULL) return 0;//分配结点没有成功,则直接返回 np->next = hashtable[hashvalue]; hashtable[hashvalue] = np; return 1; } node* malloc_node(char* name, char* desc) {//在堆上为结点分配内存,并填充结点 node *np=(node*)malloc(sizeof(node)); if(np == NULL) return NULL; np->name = name; np->desc = desc; np->next = NULL; return np; }
将字符串映射为整型地址的散列函数:
unsigned int hash(char *s) {//哈希函数 unsigned int h=0; for(;*s;s++) h=*s+h*31;//将整个字符串按照特定关系转化为一个整数,然后对hash长度取余 return h%HASHSIZE; }
查询特定的字符串对应的存储内容:
search("k110"); char* search(char* name) {//对hash表查找特定元素(元素是字符串) node* np=lookup(name); if(np==NULL) return NULL; else return np->desc; } node* lookup(char *str) { unsigned int hashvalue = hash(str); node* np = hashtable[hashvalue]; for( ; np!=NULL; np = np->next) {//这里是链地址法解决的冲突,返回的是第一个链表结点 if(!strcmp(np->name, str))//strcmp相等的时候才返回0 return np;//它是通过比较关键字key在同一个桶内的链表中查找到所需节点的,并且返回value值 } return NULL; }