哈希表(拉链法)
1.代码部分
1.1主文件
/*hash_main.cpp文件*/
#include"hasha.cpp"
#include"string.h"
#include"stdio.h"
#include"iostream"
#include<string>
int main()
{
hash a;
char buf[MAX_LINE]; /*缓冲区*/
char num[MAX_LINE];//学号
FILE *fp; /*文件指针*/
int len; /*行字符个数*/
if((fp = fopen("num.txt","r")) == NULL)
{
perror("fail to read");
exit (1) ;
}
//打开文件
int k=0,l=0,j=0,mm=0;
while(fgets(buf,MAX_LINE,fp) != NULL)
{
len = strlen(buf);
if(k>0){
//第二行开始载入
a.deal1(len,buf);//行载入
}
k++;
}
while(1)
{
printf("\nplease input the number:");
scanf("%s",num);//输入学号
a.deal2(num);//输出学号,姓名,考场等信息
}
fclose(fp);//关闭文件
return 0;
}
1.2主要函数
/*hasha.cpp*/
#include"hhsh.h"
#include"string.h"
#include"stdio.h"
#include"iostream"
#include<stdlib.h>
#include<string>
hash::hash()//构造函数把每一个key赋值为0
{
std::cout<<"load file successed"<<std::endl;
int i=400;
while(--i)stu[i].key=0;
}
void hash::deal1(int len,char *buf)//将每一行数据放入哈系表中
{
int l=0,j=0,mm=len;
char char_num[1024];
while(mm--)//载入学号和考号到缓存区用o分隔开
{
if(buf[l]<='9'&&buf[l]>='0')
{
char_num[j]=buf[l];
j++;l++;
}
else l++;
if(buf[l-1]<='9'&&buf[l-1]>='0'&&(buf[l]>'9'||buf[l]<'0'))
{
char_num[j]='o';
j++;
}
}
l=-1;
while(1)//将姓名和学号放入哈希表,如果序号为学号后三位的位置没有元素(key为 0)则将信息放在该位置并将key改为1,如果序号为1或者2则把信息放在这个 一个新节点并插入到位置的next,将key赋值2
{
ElemType *p;
++l;
if(char_num[l+3]=='o')
{
j=(char_num[l]-'0')*100+(char_num[l+1]-'0')*10+(char_num[l+2]-'0');
if(stu[j].key==0)
{
strncpy(stu[j].name,buf,6);
strncpy(stu[j].num,char_num,l+3);
stu[j].key=1;
}
else
{
ElemType *p;
p=(ElemType*)malloc(sizeof(ElemType));
p->next=stu[j].next;
stu[j].next=p;
strncpy(p->name,buf,6);
strncpy(p->num,char_num,l+3);
p->key=1;
stu[j].key=2;
}
break;
}
}
l+=3;
mm=l;
while(++l)//将学号放入哈希表
{
if(char_num[l]=='o')
{
if(stu[j].key==1){strncpy(stu[j].qq,char_num+mm+1,l-mm-1);
break;}
else {
if(stu[j].key==2)
strncpy(stu[j].next->qq,char_num+mm+1,l-mm-1);
break;
}
}
}
}
void hash::deal2(char*num)//输出学号为num学生的信息
{
int j,k=11;
ElemType *p;
j=(num[8]-'0')*100+(num[9]-'0')*10+(num[10]-'0');
switch (stu[j].key)//按照key值分三种情况,如果0说明没有该尾号的学生,如果是1则是只有一个学生,next指针为NULL,如果是二,则有至少两个学生,next接一个链表
{
case 0:
printf("cannot find the guy");
break;
case 1:
while(k--)
{
if(stu[j].num[k]!=num[k])break;
}
if(k>0)
printf("cannot find the guy");
else
printf("name:%s number:%s candidate number:%s",stu[j].name,stu[j].num,stu[j].qq); /* code */
break;
case 2:
k=12;
while(k--)
{
if(stu[j].num[k]!=num[k])break;
}
if(k<=0)printf("name:%s number:%s candidate number:%s",stu[j].name,stu[j].num,stu[j].qq);
else
{
p=stu[j].next;
while(1)
{
k=12;
while(k--)
{
if(p->num[k]!=num[k])break;
}
if(k>0)
{
if(p->next!=NULL)
p=p->next;
else
{
printf("cannot find the guy");
break;
}
continue;
}
else
{
printf("name:%s number:%s candidate number:%s",p->name,p->num,p->qq); /* code */
break;
}
//break;
}
}
break;
default:
break;
}
}
1.3声明
/* hhsh.h文件*/
#pragma warning(disable:4996)
struct ElemType{
int key;
char num[20];
char qq[20];
char name[7];
struct ElemType*next;//方便在采用链地址法时用的
};//用于存储信息的结构体
class hash{
public:
hash();
void deal1(int,char*);
void deal2(char *num);
private:
ElemType stu[400];
};//哈希表
ps:
表格类似于这种
姓名 学号 考号
孙尖 16040410043 2019070001
廖劳 16070110015 2019070002
樊范 16070199006 2019070003