算法导论学习笔记(4)——利用链接法实现哈希表

常用的解决哈希冲突的方法有两种:

一、开放定址法:开放定址法是一类以发生冲突的哈希地址为自变量,通过某种哈希冲突函数得到一个新的空闲地址的方法。

在开放定址法中常用的有线性探查法和平法探查法;线性探查容易产生堆积问题。而平方探查法可以解决堆积问题,但不能探查到哈希表上的所有单元,但至少能探查到一本单元

二、拉链法:拉链法是把所有的同义词用单链表链接起来的一种方法,与开放定址法相比有以下优点:

(1)、处理冲突简单,且无堆积现象,即非同义词不会发生冲突,因此平均查找长度较短;

(2)、由于拉链法中各链表上的记录空间是动态申请的,故更适合于造表前无法确定表长的情况;

(3)、删除记录容易

缺点是需要额外的空间,故当记录较多时可以用拉链法;

以下为拉链法的C++代码:

#include <iostream>

typedef struct _Node
{
 int data;
 struct _Node *next;
}NODE,*PNODE;

typedef struct  _HASH_TABLE
{
 PNODE value[10];
}HASH_TABLE, *PHASH_TABLE;

PHASH_TABLE create_hash_table()
{
 PHASH_TABLE pHashTable = (PHASH_TABLE)malloc(sizeof(HASH_TABLE));
 memset(pHashTable,0,sizeof(HASH_TABLE));
 return pHashTable;
}

PNODE find_data_in_hash(PHASH_TABLE pHashTbl,int data) 

 PNODE pNode; 
 if (NULL == pHashTbl) 
 { 
  return NULL; 
 } 

 /*获得HASH表索引,为NULL则直接返回NULL*/ 
 if (NULL == (pNode = pHashTbl->value[data%10])) 
 { 
  return NULL; 
 } 

 /*在该索引下的单链表中查找节点*/ 
 while(pNode) 
 { 
  if ( data == pNode->data) 
  { 
   /*找到节点就返回当前节点*/ 
   return pNode; 
  } 
  /*当前节点不是,指向下一节点*/ 
  pNode = pNode->next; 
 } 

 /*没找到返回NULL,不过在这返回没有意义*/ 
 return NULL;

bool insert_data_into_hash(PHASH_TABLE pHashTbl,int data) 

 PNODE pNode; 
 if (NULL == pHashTbl) 
 { 
  return false; 
 } 

 if (NULL == pHashTbl->value[data%10]) 
 { 
  pNode = (NODE*)malloc(sizeof(NODE)); 
  memset(pNode,0,sizeof(NODE)); 
  pNode->data = data; 
  pHashTbl->value[data%10] = pNode; 

  return true; 
 } 

 if (NULL != find_data_in_hash(pHashTbl,data)) 
 { 
  return false; 
 } 

 pNode = pHashTbl->value[data%10]; 
 while(pNode->next) 
 { 
  pNode = pNode->next; 
 } 

 pNode->next = (NODE*)malloc(sizeof(NODE)); 
 memset(pNode->next,0,sizeof(NODE)); 
 pNode->next->data = data; 

 return true; 

bool delete_data_from_hash(PHASH_TABLE pHashTbl,int data) 

    PNODE pHead; 
    PNODE pNode; 
 
    if (NULL == pHashTbl || NULL == pHashTbl->value[data%10]) 
    { 
        return false; 
    } 
 
    if (NULL == (pNode = find_data_in_hash(pHashTbl,data))) 
    { 
        return false; 
    } 
 
    if (pNode == pHashTbl->value[data%10]) 
    { 
        pHashTbl->value[data%10] = pNode->next; 
  free(pNode); 
  return false;   
    } 
 
    pHead = pHashTbl->value[data%10]; 
     
    while(pNode != pHead->next) 
    { 
        pHead = pHead->next; 
    } 
 
    pHead->next = pNode->next; 
 
 return true;

 
 
/****************************************
 f)打印hash表中所有数据
 如:
 [Hash idx]     [value]
 0-------------NULL
 1-------------1 251
 2-------------22
 3-------------123 43
 4-------------NULL
 5-------------55 15 235 525 725 275 545
 6-------------NULL
 7-------------257
 8-------------NULL
*****************************************/ 
void print_hash_data(HASH_TABLE* pHashTbl) 

    NODE* pNode; 
    int i=0; 
    if (NULL == pHashTbl) 
    { 
        printf("ERROR:The hash is NULL\n"); 
    } 
 
/*
    if (NULL == (pNode = pHashTbl->value[10]))
    {
        printf("ERROR:The hash node is NULL\n");
    }
*/ 
    printf("[Hash idx]     [value]\n"); 
    do  
    {    
        printf("   %d-------------",i); 
        if (NULL == pHashTbl->value[i]) 
        { 
            i++; 
            printf("NULL\n"); 
            continue; 
        } 
 
        pNode = pHashTbl->value[i]; 
         
        while(pNode) 
        { 
            printf("%d ",pNode->data); 
            pNode = pNode->next; 
        } 
        printf("\n"); 
        i++; 
    } while (i<10); 
 
    printf("\n"); 
}

int main()
{
 HASH_TABLE* pHashTbl = create_hash_table(); 

 (void)insert_data_into_hash(pHashTbl,22); 
 (void)insert_data_into_hash(pHashTbl,22); 
 (void)insert_data_into_hash(pHashTbl,123); 
 (void)insert_data_into_hash(pHashTbl,436); 
 (void)insert_data_into_hash(pHashTbl,55); 
 (void)insert_data_into_hash(pHashTbl,157); 
 (void)insert_data_into_hash(pHashTbl,235); 
 (void)insert_data_into_hash(pHashTbl,256); 
 (void)insert_data_into_hash(pHashTbl,525); 
 (void)insert_data_into_hash(pHashTbl,724); 
 (void)insert_data_into_hash(pHashTbl,278); 
 (void)insert_data_into_hash(pHashTbl,209); 
 (void)insert_data_into_hash(pHashTbl,67); 
 (void)insert_data_into_hash(pHashTbl,54); 
 (void)insert_data_into_hash(pHashTbl,546); 
 (void)insert_data_into_hash(pHashTbl,350); 
 (void)insert_data_into_hash(pHashTbl,101); 
 (void)insert_data_into_hash(pHashTbl,23); 

 print_hash_data(pHashTbl); 

 (void)delete_data_from_hash(pHashTbl,55); 

 print_hash_data(pHashTbl);
 system("pause");
 return 1;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值