c_数据结构_哈希表
#include <stdio.h> #include <stdlib.h> #include <string.h> #define ERROR 0 #define OK 1 #define Size 21 // 指定质数(数组长度) typedef struct{ char name[20]; char address[20]; char num[12]; }mul; typedef struct{ mul data[20]; int size; }Hashtable; void init(Hashtable &h) { for(int i=0;i<Size;i++){ h.data[i].num[0]=0;//首位赋为0 } h.size = Size; } // 判断电话簿是否为空 int kong(Hashtable &h){ for(int i=0;i<Size;i++){ if(h.data[i].num[0]!=0){ return ERROR; } } return OK; } int HashSearch(Hashtable &h); // 新存入的数的和是否已经被存储了 int c_t(Hashtable &h,int sum){ int m,n,sum1=0; for(int k=0;k<Size;k++){ //循环整个数组 n = strlen(h.data[k].num); if(h.data[k].num[0]!=0){ for(m=0;m<n;m++){ sum1=sum1+h.data[k].num[m]-'0'; } if(sum1==sum){ printf("您输入的电话号码已经被存储,请重新输入\n\n"); HashSearch(h); fflush(stdin); return ERROR; } } } return OK; } // 寻址存数 int HashSearch(Hashtable &h) { char nu[12],na[20],add[50]; int i,p,j,y=0,boo=1;//nu关键字 int m,n,sum=0,sum1=0; printf("请输入要存入的电话记录的姓名、地址和11位手机号码(用空格隔开)\n"); scanf("%s",na); scanf("%s",add); scanf("%s",nu); n=strlen(nu); // 电话号的长度 if(n==11){ for(m=0;m<n;m++){ sum=sum+nu[m]-'0'; // 计算电话号码的总和进行存储 } boo=c_t(h,sum); // 判断输入的数是否被存储了 if(boo){ j=sum%Size;//哈希函数 if(h.data[j].num[0]==0){ p=j; h.size=j; }else{ i=(j+1)%Size; // 向后探测一个位置 if(h.data[i].num[0]==0){ p=i; h.size=i; } while(h.data[i].num[0]!=0 && i!=j) { i=(i+1)%Size; //向后探测位置 if(h.data[i].num[0]==0){ p=i; h.size=i; break; } } if (i==j){ printf("当前电话谱最多只能实现 %d 个数据存储\n",Size); return ERROR; } } strcpy(h.data[p].num,nu); // 把存入的数据放入定义的数组指定位置 strcpy(h.data[p].address,add); strcpy(h.data[p].name,na); printf("存入数据 %d 号位置: %s %s %s\n",h.size,h.data[p].name,h.data[p].address,h.data[p].num); } }else{ printf("\n!!!请输入11位手机号码!!!\n"); HashSearch(h); } return OK; } // 批量存入电话记录 int pl_HashSearch(Hashtable &h){ int n=0; printf("请输入您要添加电话记录的条数:"); scanf("%d",&n); if(1<n&&n<21){ for(int i=0;i<n;i++){ HashSearch(h); } }else{ printf("\n您存入的条数大于20条 或者小于2条\n\n"); pl_HashSearch(h); } return OK; } // 打印所有记录 void disp(Hashtable &h) { printf("电话簿中电话记录如下:\n"); for(int i=0;i<Size;++i){ if(h.data[i].num[0]){ printf("%d号位置\n姓名:%s 地址:%s 电话:%s\n",i,h.data[i].name,h.data[i].address,h.data[i].num); } } } // 哈希查找 int hash_kind(Hashtable h){ char num[12]; int i,j,y=0;//nu关键字 int m,n,sum=0; printf("请输入您要在电话簿中查找的电话号码:\n"); scanf("%s",&num); n=strlen(num); // 电话号的长度 for(m=0;m<n;m++){ sum=sum+num[m]-'0'; // 计算电话号码的总和进行存储 } j=sum%Size;//哈希函数 if(strcmp(h.data[j].num,num)==0){ // 探测查找 printf("您要查找的相关信息:%d号位置: \n姓名:%s\n地址:%s\n电话号码:%s\n",j,h.data[j].name,h.data[j].address,h.data[j].num); } else{ i=(j+1)%Size; while(h.data[i].num[0]!=0 && i!=j) { if(strcmp(h.data[i].num,num)==0){ printf("您要查找的相关信息:%d号位置 : \n姓名:%s\n地址:%s\n电话号码:%s\n",i,h.data[j].name,h.data[j].address,h.data[j].num); break; } i=(i+1)%Size; //向后探测一个位置 } if(h.data[i].num[0]==0){ printf("\n(嘟。。)当前号码谱没有此号码!!查无此人!!查无此人!!\n"); return ERROR; } } return OK; } //操作菜单 void OperateMenu(){ printf("\n\n--------------请选择元素处理方式---------\n\n"); printf("注:电话号应为 11 位\n\n"); printf("0> :退出\n\n"); printf("1>: 存入电话号\n\n"); printf("2>: 批量存入电话号\n\n"); printf("3>: 哈希查找电话号\n\n"); printf("4>: 显示电话簿\n\n"); printf("请选择对元素的处理:"); } void main(){ int w=0,k,boo=1,i=1,e=0; Hashtable h; printf("注:此测试过程输入值应全为数字\n\n"); printf("进入号码簿存储请输入:'1'\n\n"); printf("退出请选择'0'或 其它!!\n\n"); printf("请选择:"); scanf("%d",&w); if(w==1){ init(h); OperateMenu(); scanf("%d",&k); while(k){ switch(k){ case 0:break; case 1:boo=HashSearch(h); if(boo) printf("存入成功!!\n"); else printf("存入失败!!\n"); break; case 2:boo=pl_HashSearch(h); if(boo) printf("批量存入成功!!\n"); else printf("批量存入失败!!\n"); break; case 3:boo=kong(h); if(boo==1){ printf("\n!!当前电话簿为空!!\n"); }else{ boo=hash_kind(h); if(boo) printf("哈希查找成功!!\n"); else printf("哈希查找失败!!\n"); } break; case 4: boo=kong(h); if(boo==1){ printf("\n!!当前电话簿为空!!\n"); }else{disp(h); }break; } OperateMenu(); scanf("%d",&k); } } }