某客店有N个等级的房间,第k级客房有A(k)个,每个房间有B(k)个单人床,以菜单调用方式设计为单身旅客分配床位以及离店时收回床位的程序。要求分配成功时,印出旅客姓名、年龄、性别、到达日期、客房等级、房间号及床位号;分配不成功时,允许更改房间等级,若不更改等级,印出“满客”提示。
受某大佬的博客的构建方式启发(自己想了但最后失败了)所写,不算完全原创,可以与大佬的做对照。大佬的原博客:https://blog.csdn.net/linnzl/article/details/51477788
希望对后来者有所启发,注释写的很清楚啦
#include <stdio.h>
#include <stdlib.h>
#include<string.h>
#include<time.h>
struct Level{
struct Room *R; ///房间数组
int Roomnum; ///房间个数;
};
struct Room{
int sex; ///性别
int allcount; /// 总床位个数
int count; ///空床位个数
int Rnum; ///房间号
struct Bed *B; ///床位数组
};
struct Bed { ///床位情况;
int Bnum; ///床位号
char name[100]; ///姓名
int in; ///是否入住
char id[100]; ///ID
};
int n, x ,y, e, f; ///全局变量: n 总等级 x 输入性别 y 输入等级 e f计数器
struct Level* Createhotel(struct Level *h){ /// 创建旅馆
printf("输入总级数:");
scanf("%d", &n);
int a, b; /// 房间数和房间的床位数
h = (struct Level*)malloc(sizeof(struct Level)*n); ///开辟level数组空间,h为头指针
for(int i = 0; i < n; i++){
printf("输入%d级下的房间数和房间的床位数:", i + 1);
scanf("%d %d", &a, &b);
h[i].Roomnum = a;
h[i].R = (struct Room*)malloc(sizeof(struct Room)*a); ///开辟空间
for(int j = 0; j < a; j++){
h[i].R[j].sex = 0; ///性别初始化
h[i].R[j].count = b;
h[i].R[j].allcount = b;
h[i].R[j].Rnum = (i + 1)*100 + j; ///房间号
h[i].R[j].B = (struct Bed*)malloc(sizeof(struct Bed)*b);
for(int k = 0; k < b; k++){
h[i].R[j].B[k].Bnum = k + 1; /// 床号
h[i].R[j].B[k].in = 0; /// 床是否入住 1 是 0 否
}
}
}
return h;
}
int Checklevfull(struct Level a){ ///判断某级是否已满
for(int i = 0; i < a.Roomnum; i++){
if(a.R[i].count != 0) ///空床位数>0返回1反之0
return 1;
}
return 0;
}
int Checkallfull(struct Level *a){ ///判断全店是否已满 int为返回值类型
for(int i = 0; i < n; i++){
if(Checklevfull(a[i])) ///调用checklevfull逐级判断,返回值同理
return 1;
}
return 0;
}
void Checklevempty(struct Level a, int x){ ///查询某等级a的空余床位 性别x: 0 不限 1 男 2 女
e = 0; ///计数器
for(int i = 0; i < a.Roomnum; i++){
if(x == 0){ ///不限性别查询
if(a.R[i].count > 0){ ///有空床
if(a.R[i].count == a.R[i].allcount) printf("*0*:房%d:", a.R[i].Rnum); /// count=allcount则房间为空 0:空房间
else printf("*%d*:房%d:", a.R[i].sex, a.R[i].Rnum); ///房间不为空
for(int j = 0; j < a.R[i].allcount; j++){
if(a.R[i].B[j].in == 0){ ///该床空,则输出床号
printf("%d号\t", a.R[i].B[j].Bnum);
e++; ///有空床则加1
}
}
printf("\n");
}
} else{
if((a.R[i].sex == x || a.R[i].sex == 0) && a.R[i].count > 0){ /// x 1男 2女, 性别为0即空房,以下同上
if(a.R[i].count == a.R[i].allcount) printf("*0*:房%d:", a.R[i].Rnum);
else printf("*%d*:房%d:", x, a.R[i].Rnum);
for(int j = 0; j < a.R[i].allcount; j++){
if(a.R[i].B[j].in == 0){
printf("%d号\t", a.R[i].B[j].Bnum);
e++;
}
}
printf("\n");
}
}
}
}
void Checkempty(struct Level *a){ ///查询空余床位 0 不限 1 男 2 女
int z;
printf("----0 查询全店 1 查询特定等级----\n请输入:");
scanf("%d", &z);
printf("\n");
if(z == 1){ ///查等级
printf("输入需要查询的等级和性别(0 不限 1 男 2 女):");
scanf("%d %d", &y, &x);
printf("\n");
Checklevempty(a[y-1], x); ///数组从0开始故y-1
if( e==0 ) printf("满客!\n"); /// 计数器为零,该等级该性别满员
printf("\n");
} else { ///查全店
f = 0; ///计数器
printf("输入需要查询的性别(0 不限 1 男 2 女):");
scanf("%d", &x);
if(x == 1){printf("全店的男性床位空余情况:\n");} ///查不同性别的标题
else if(x == 2){printf("全店的女性床位空余情况:\n");}
else {printf("全店的床位空余情况:(房间性别表示:0 不限 1 男 2 女)\n");}
for(int i = 0; i < n; i++){ /// 调用checklevempty逐级查询
printf("第%d级:\n", i + 1);
Checklevempty(a[i], x);
f+=e; ///计数器
printf("\n");
}
if(f == 0) printf("满客!\n");
}
}
int Levsexfull(struct Level a, int x){ ///查询某等级男、女客是否已满
for(int i = 0; i < a.Roomnum; i++){
if(x == 1){
if(a.R[i].sex == 1 || a.R[i].sex == 0){ ///房间性别为男或空房且count>0,有空位返回1反之0
if(a.R[i].count > 0) return 1;
}
}else {
if(a.R[i].sex == 2 || a.R[i].sex == 0){
if(a.R[i].count > 0) return 1;
}
}
}
return 0;
}
int Sexfull(struct Level *a, int x){ ///查询全店男、女客是否已满
for(int i = 0; i < n; i++){
if(Levsexfull(a[i], x)) return 1; ///调用逐级查询
}
return 0;
}
void Guestimfo(struct Level *a){ ///根据姓名查询客户信息
char name[100];
printf("输入需要查询的客户姓名:");
scanf("%s", name);
e = 0;
for(int i = 0; i < n; i++){
for(int j = 0; j < a[i].Roomnum; j++){
for(int k = 0; k < a[i].R[j].allcount; k++){
if(strcmp(name, a[i].R[j].B[k].name) == 0){ ///调用strcmp字符串比较
printf("------客户信息------\n");
printf("姓名:%s\n", a[i].R[j].B[k].name);
printf("性别:");
if(a[i].R[j].sex == 1)printf("男\n");
else printf("女\n");
printf("ID:%s\n", a[i].R[j].B[k].id);
printf("等级:%d 房间号:%d 床号:%d\n", i+1, a[i].R[j].Rnum, a[i].R[j].B[k].Bnum);
e++; ///查询到则加1,可能同名故不加break
}
}
}
}
if(e == 0) printf("抱歉,未查询到该客户的入住信息!\n");
}
struct Level* Order(struct Level *a){ ///订房入住
int g, l;
if(!Checkallfull(a)){ ///店外通知
printf("满客!");
return a;
}
if(Sexfull(a, 1) == 0){ ///通知
printf("本店男性满客!\n");
}
if(Sexfull(a, 2) == 0){ ///通知
printf("本店女性满客!\n");
}
printf("请输入订房等级(1-%d)及性别 (1 男 2 女):", n);
scanf("%d %d", &y, &x);
if(Sexfull(a, x) == 0){ ///该性别满客
if(x == 1){
printf("本店男性满客!\n");
return a;
}
else{
printf("本店女性满客!\n");
return a;
}
}
while(Levsexfull(a[y-1], x) == 0){ ///该等级该性别已满
if(Levsexfull(a[y-1], x) == 0) printf("该等级已满!是否查看其他等级(0 查看 1 退出):");
scanf("%d", &g);
printf("\n");
if(g == 1){
return a; ///返回菜单
} else{
printf("请重新输入等级(1-%d):", n);
scanf("%d", &y);
}
}
printf("---选择房间: 0 系统分配 1 自行选择---\n请输入:");
scanf("%d", &l);
if(l == 0){ ///系统分配,按顺序分配房间
for(int i = 0; i < a[y-1].Roomnum; i++){
if((a[y-1].R[i].count > 0 && a[y-1].R[i].sex == x) || a[y-1].R[i].sex == 0){
for(int j = 0; j < a[y-1].R[i].allcount; j++){
if(a[y-1].R[i].B[j].in == 0){
a[y-1].R[i].sex = x; ///性别存储
a[y-1].R[i].count--; ///空床位数减1
printf("请输入您的姓名:");
scanf("%s", a[y-1].R[i].B[j].name);
printf("请输入您的ID:");
scanf("%s", a[y-1].R[i].B[j].id);
a[y-1].R[i].B[j].in = 1; ///床位状态:入住
printf("----订房成功-----\n");
printf("客户姓名:%s\n", a[y-1].R[i].B[j].name);
printf("性别:");
if(x == 1)printf("男\n");
else printf("女\n");
printf("ID:%s\n", a[y-1].R[i].B[j].id);
printf("房间信息:%d级%d房%d%号床\n", y, a[y-1].R[i].Rnum, a[y-1].R[i].B[j].Bnum);
return a;
}
}
}
}
} else{ ///自助
int o, p, q;
Checklevempty(a[y-1], x); ///查询空床位
printf("输入您选择的房间号:");
scanf("%d", &o);
p = o%100; ///房间号
q = (o-p)/100; ///等级
while(q != y || p > a[y-1].Roomnum-1){ ///不是已输入等级,房间号不存在
printf("输入有误,请重新输入:");
scanf("%d", &o);
p = o%100;
q = (o-p)/100;
}
for(int j = 0; j < a[y-1].R[p].allcount; j++){ ///同系统分配的内容
if(a[y-1].R[p].B[j].in == 0){
a[y-1].R[p].sex = x;
a[y-1].R[p].count--;
printf("请输入您的姓名:");
scanf("%s", a[y-1].R[p].B[j].name);
printf("请输入您的ID:");
scanf("%s", a[y-1].R[p].B[j].id);
a[y-1].R[p].B[j].in = 1;
printf("----订房成功-----\n");
printf("客户姓名:%s\n", a[y-1].R[p].B[j].name);
printf("性别:");
if(x == 1)printf("男\n");
else printf("女\n");
printf("ID:%s\n", a[y-1].R[p].B[j].id);
printf("房间信息:%d级%d房%d%号床\n", y, a[y-1].R[p].Rnum, a[y-1].R[p].B[j].Bnum);
return a;
}
}
}
}
void info_num(struct Level *a){ ///查询某性别入住总数及客户信息
e = 0; ///计数器
f = 0;
printf("输入查询的性别(0 全店 1 男 2 女):");
scanf("%d", &x);
printf("查询结果如下:\n");
for(int i = 0; i < n; i++){
for(int j = 0; j < a[i].Roomnum; j++){
for(int k = 0; k < a[i].R[j].allcount; k++){
if(a[i].R[j].B[k].in == 1 && (a[i].R[j].sex == x || x == 0)){
printf("客户姓名:%s\t", a[i].R[j].B[k].name);
printf("性别:");
if(a[i].R[j].sex == 1)printf("男\t");
else printf("女\t");
printf("ID:%s\t", a[i].R[j].B[k].id);
printf("房间信息:%d级%d房%d%号床\t", y, a[i].R[j].Rnum, a[i].R[j].B[k].Bnum);
if(a[i].R[j].sex == 1) e++;
if(a[i].R[j].sex == 2) f++;
}
}
}
}
if(x == 1)printf("全店共入住了%d名男性\n", e);
else if(x == 2)printf("全店共入住了%d名女性\n", f);
else printf("入住总人数为%d,其中男性%d名,女性%d名\n", e + f, e, f );
}
struct Level* Checkout(struct Level *a){ ///退房
char name[100] , id[100];
int o, p, q, e = 0;
printf("输入需要退房的房间号:");
scanf("%d", &o);
p = o%100;
q = (o-p)/100-1;
while(q < 0 || q > n-1 || p > a[q].Roomnum-1){
printf("输入有误,请重新输入:");
scanf("%d", &o);
p = o%100;
q = (o-p)/100-1;
}
printf("请输入您的姓名:");
scanf("%s", name);
printf("输入客户ID:");
scanf("%s", &id);
for(int k = 0; k < a[q].R[p].allcount; k++){
if(strcmp(name, a[q].R[p].B[k].name) == 0 && strcmp(id, a[q].R[p].B[k].id) == 0){ ///匹配姓名与ID
e++; ///匹配成功,即查询到该客户信息
printf("%d级%d号房%d号床办理退房\n",q + 1, a[q].R[p].Rnum, a[q].R[p].B[k].Bnum);
printf("退房成功!谢谢光临!\n");
a[q].R[p].B[k].in = 0; ///信息初始化
a[q].R[p].count++; ///空床位数加1
if(a[q].R[p].count == a[q].R[p].allcount) a[q].R[p].sex = 0; ///空床位数等于总床数,则改信息为空房
break;
}
}
if(e == 0) printf("抱歉,未在%d房查询到该客户的入住信息!\n", a[q].R[p].Rnum);///未查询到客户
return a;
}
int main(){
int op;
struct Level *h;
h = Createhotel(h);
while(1){
printf("========================\n");
printf("欢迎来到XX酒店!!!\n");
printf("------1 入 住------\n");
printf("------2 退 房------\n");
printf("------3 查询客户信息------\n");
printf("------4 查 询 空 房------\n");
printf("------5 查询入住总数------\n");
printf("------6 退 出------\n");
printf("请输入:");
scanf("%d", &op);
while(op != 1 && op != 2 && op != 3 && op != 4 && op != 5 && op != 6){
printf("输入有误,请重新输入:");
scanf("%d", &op);
}
switch(op){
case 1: h = Order(h);break;
case 2: h = Checkout(h);break;
case 3: Guestimfo(h);break;
case 4: Checkempty(h);break;
case 5: info_num(h);break;
case 6: printf("谢谢使用!");exit(1);break;
}
printf("========================\n\n");
}
}