破“哈希”式

哈希表

哈希表有点像我们上学的时候按学号分小组,通过这种方式老师可以很轻松的下达任务,或者很快的发现谁没交作业(一个班的作业很难一眼看出少了几本,但是一个组就那么几本作业,少了一两本一眼就看出来了)。

如图将24人分成6组
在这里插入图片描述
这种编号的方式就是高效的散列,我们俗称“哈希”!

以上过程是通过把关键码值 key(编号)映射到表中一个位置(数组的下标)来访问记录,以加 快查找的速度。这个映射函数叫做散列函数,存放记录的数组叫做散列表。

在这里插入图片描述
在这里插入图片描述

哈希链表的算法实现

哈希链表数据结构的定义

#define DEFAULT_SIZE 16 

typedef struct _ListNode { 
	struct _ListNode *next; 
	int key; 
	void *data; 
}ListNode; 

typedef ListNode *List; 
typedef ListNode *Element; 

typedef struct _HashTable { 
	int TableSize; 
	List *Thelists; 
}HashTable;

哈希函数

/*根据 key 计算索引,定位 Hash 桶的位置*/ 
int Hash(int key, int TableSize) { 
	return (key%TableSize); 
}

哈希链表初始化

/*初始化哈希表*/ 
HashTable *InitHash(int TableSize) { 
	int i = 0; 
	HashTable *hTable = NULL;
	 
	if (TableSize <= 0) { 
		TableSize = DEFAULT_SIZE; 
	}
	
	hTable = (HashTable *)malloc(sizeof(HashTable)); 
	
	if (NULL == hTable) { 
		printf("HashTable malloc error.\n"); 
		return NULL; 
	}
	
	hTable->TableSize = TableSize; 
	
	//为 Hash 桶分配内存空间,其为一个指针数组 
	hTable->Thelists = (List *)malloc(sizeof(List)*TableSize); 
	
	if (NULL == hTable->Thelists) { 
		printf("HashTable malloc error\n"); 
		free(hTable); 
		return NULL; 
	}
	
	//为 Hash 桶对应的指针数组初始化链表节点 
	for (i = 0; i < TableSize; i++) { 
		hTable->Thelists[i] = (ListNode *)malloc(sizeof(ListNode)); 
		
		if (NULL == hTable->Thelists[i]) { 
			printf("HashTable malloc error\n"); 
			free(hTable->Thelists); 
			free(hTable); 
			return NULL; 
		}else { 
			memset(hTable->Thelists[i], 0, sizeof(ListNode)); 
		} 
	}
	return hTable; 
}

哈希链表查找元素

/*从哈希表中根据键值查找元素*/ 
Element Find(HashTable *HashTable, int key) { 
	int i = 0; 
	List L = NULL; 
	Element e = NULL; 
	i = Hash(key, HashTable->TableSize); 
	L = HashTable->Thelists[i]; 
	e = L->next; 
	
	while (e != NULL && e->key != key) 
		e = e->next; 
		
	return e; 
}

哈希链表插入元素

/*哈希表插入元素,元素为键值对*/ 
void Insert(HashTable *HashTable, int key, void *value ){ 
	Element e=NULL, tmp=NULL; 
	List L=NULL; 
	e = Find(HashTable, key); 
	
	if (NULL == e) { 
		tmp = (Element)malloc(sizeof(ListNode)); 
		
		if (NULL == tmp) { 
			printf("malloc error\n"); 
			return; 
		}
	
		L = HashTable->Thelists[Hash(key, HashTable->TableSize)]; 
		tmp->data = value; 
		tmp->key = key; 
		tmp->next = L->next; 
		L->next = tmp; 
	}else
		printf("the key already exist\n"); 
}

哈希链表删除元素

/*哈希表删除元素,元素为键值对*/ 
void Delete(HashTable *HashTable, int key ) { 
	Element e=NULL, last=NULL; 
	List L=NULL; 
	int i = Hash(key, HashTable->TableSize); 
	L = HashTable->Thelists[i]; 
	last = L; 
	e = L->next; 
	
	while (e != NULL && e->key != key){ 
		last = e; 
		e = e->next; 
	}
	
	if(e){//如果键值对存在 
		last->next = e->next; 
		delete(e); 
	} 
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值