一、课题内容和要求
(一)课题要求
家谱管理系统是查询家谱信息必不可少的一部分,利用家谱管理系统可以清楚的了解家族成员信息。该家谱管理系统是通过树来实现的。要求系统界面友好,易于操作。
(二)课题要求
a)需要设置普通用户、超级管理员不同角色,不同角色登录后的权限各不相同,普通用户可以进行查询;超级管理员有对所有成员增加、删除和修改的权限。
b)家谱中的成员的信息均应包括姓名、出生日期、婚否、地址、健在否、死亡日期(若其已死亡)等,也可附加其他信息,并且存储与文本文件中。
c)查询功能。可按照姓名查询,输出成员信息(包括其本人、父亲、孩子的信息、所在辈分);按照出生日期查询成员名单。
d)按照出生日期对家谱中所有人进行排序
e)打开家谱时,提示当天生日的健在成员
f)以图形方式显示家谱
(三)其他要求
(1)变量、函数命名符合规范
(2)注释详细:每个变量都要求有注释说明用途:函数有注释说明功能,对参数、返回值也要以注释的形式说明用途;关键语句段要求有注释解释
(3)程序的层次清晰,可读性强。
(4)界面美观,交互方便。
头文件treeheader.h
#ifndef TREECO_H_
#define TREECO_H_
#include <iostream>
#include <stdio.h>
#include <fstream>
#include <time.h> //获取搜索时刻的时间
#include <stdbool.h> //布尔类型
#include <stdlib.h> //动态分配内存
#include <string.h> //字符串处理
#include <memory.h>#define MAX_TREE_SIZE 20 //最大父亲数量
#define LEN 20 //基本属性的长度
#define ERROR 0
#define OK 1
using namespace std;
typedef int Status; // 状态
typedef struct //个人信息结构体
{char name[LEN]; //姓名char bothDay[LEN]; //出生日期int getMatings; //是否结婚char address[LEN]; //其住址int keepAlive; //是否健在char deathDay[LEN]; //若死亡,死亡日期
}ElemType;
typedef struct CTNode //孩子节点
{int child; //自身的标记,数组下标struct CTNode *next; //指针域
}ChildPtr;typedef struct //表头结构
{int parent; //父母的信息,数组下标ElemType data; //个人信息ChildPtr* firstchild; //
}CTBox;typedef struct //树结构
{CTBox nodes[MAX_TREE_SIZE]; //节点数组int r, n; //根的位置和节点数
}CTree;
void User_login(CTree *tree); //用户账户密码管理
void main_menu_super(CTree *tree); //管理员菜单
void main_menu_normal(CTree *tree); //普通用户菜单
char get_choice_menu_super(); //超级用户菜单的选择
char get_choice_menu_normal();//普通用户菜单的选择
char get_choice_Inquire(); //查询系统的选择
char get_choice_Modify(); //修改菜单的选择
ElemType Input();//录入成员信息函数
void Init(CTree *tree); //初始化家族谱
void show_seniority(CTree *tree, int flag); //显示查询此人时候的辈分
Status Exist_Name(CTree *tree); //以姓名查询是否存在此人
Status Exist_BothDay(CTree *tree); //以出生日期判断是否存在此人
void Inquire(CTree *tree); //查询功能
void Add_Child(CTree *tree, int i); //为数组节点增加孩子
void Add_Parent_Init(CTree *tree, int i); //为数组节点确定父节点
void Add_Parent_Person(CTree *tree, int i);//增加新成员时父亲节点的动态变化
Status Add_Person(CTree *tree);//增加新成员
Status Remove(CTree *tree); //删除某人
Status Modify(CTree *tree); //修改某人信息
Status Sort_BothDay(CTree *tree); //对家谱里的人按照出生日期进行排序
void Destroy(CTree *tree);
void Data_write(CTree *tree);
#endif
头文件中函数实现文件:implements.cpp
#include "treeheader.h"
void User_login(CTree *tree)
{char passpord[LEN] = {"123123"}; //超级用户的密码char normalUser[LEN] = {"user_normal"}; //普通用户的账号char superUser[LEN] = {"user_super"}; //超级用户的账号char input_user[LEN]; //接收用户名输入char input_password[LEN]; //接收超级用户的密码输入printf("***********\t欢迎登陆家族管理系统\t***********\n");printf("输入您的用户名:");gets(input_user);if(!strcmp(input_user, normalUser)) // 判断此输入是否与普通用户名相同{main_menu_normal(tree); //显示普通用户的菜单}else if(!strcmp(input_user, superUser)) //判断此输入是否与超级用户名相同{printf("请输入管理员密码:");gets(input_password); //接收密码输入if(!strcmp(input_password,passpord)) // 判断密码是否正确{main_menu_super(tree); //显示超级用户的菜单}else{printf("密码输入错误!程序终止!!\n");exit(-1); //密码错误,退出程序}}
}void main_menu_super(CTree *tree) //超级用户的菜单
{int status; //判断选择后执行的成功与否int choice; //根据选择而执行相关功能while((choice = get_choice_menu_super()) != 'q'){switch (choice){case 'a':Init(tree); //调用初始化函数break;case 'b':Inquire(tree); //调用查询功能break;case 'c':status = Add_Person(tree); //调用增加成员函数,如果成功添加,则返回OK,反之,返回ERRORif(status){printf("添加新成员成功!\n");}break;case 'd':status = Remove(tree); //调用删除成员函数,如果成功删除,则返回OK,反之,返回ERRORif(status){printf("删除此人操作成功!\n");}else{printf("家谱中没有不存在此人!\n");}break;case 'e':status = Modify(tree); //调用修改成员函数,如果成功修改,则返回OK,反之,返回ERRORif(status){printf("修改此人操作成功!\n");}else{printf("家谱中没有不存在此人!\n");}break;case 'f':status = Sort_BothDay(tree); //调用按照生日排序成员函数,如果成功排序,则返回OK,反之,返回ERRORif(status){printf("排序操作成功!\n");}else{printf("排序操作失败!\n");}break;case 'g':Destroy(tree);break;case 'h':Data_write(tree);case 'q':default:break;}}
}void main_menu_normal(CTree *tree)
{int status; //判断选择后执行的成功与否int choice;//根据选择而执行相关功能while((choice = get_choice_menu_normal()) != 'q'){switch (choice){case 'a':Init(tree); //调用初始化函数break;case 'b':Inquire(tree); //调用查询功能break;case 'c':status = Sort_BothDay(tree); //调用按照生日排序成员函数,如果成功排序,则返回OK,反之,返回ERRORif(status){printf("排序操作成功!\n");}else{printf("排序操作失败!\n");}break;case 'q':default:break;}}
}char get_choice_menu_super()
{int ch; //定义接收输入的变量printf("\t\t欢迎使用此家族管理系统!!!\t\t\t\n");printf("*************************************\n");printf("Enter the letter of your choice:\n");printf("a. 初始化家族谱\t\tb. 查询信息\n");printf("c. 增加新成员 \t\td. 删除成员\n");printf("e. 修改成员 \t\tf. 按生日进行排序\n");printf("g. 释放内存 \t\th. 存入文本文件\n");printf("**************q. 退出程序***********\n");ch = getchar(); //接收输入while(getchar() != '\n') //清空缓冲区{continue;}return ch; //返回输入选项,启动相关函数调用
}char get_choice_menu_normal()
{int ch; //定义接收输入的变量printf("\t\t欢迎使用此家族管理系统!!!\t\t\t\n");printf("*************************************\n");printf("Enter the letter of your choice:\n");printf("a. 初始化家族谱\t\tb. 查询信息\n");printf("c. 按生日进行排序\t\tq. 退出程序\n");printf("************************************\n");ch = getchar(); //接收输入while(getchar() != '\n')//清空缓冲区{continue;}return ch; //返回输入选项,启动相关函数调用
}char get_choice_Inquire()
{int ch;//定义接收输入的变量printf("欢迎使用此家族管理系统的查询系统!!!\n");printf("a. 根据姓名查询 b. 根据生日查询\n");ch = getchar();//接收输入while(getchar() != '\n')//清空缓冲区{continue;}return ch;//返回输入选项,启动相关函数调用
}char get_choice_Modify()
{int ch;//定义接收输入的变量printf("欢迎使用此家族管理系统的修改系统!!!\n");printf("a. 编辑姓名 b. 编辑出生日期\n");printf("c. 编辑是否健在 d. 编辑是否已婚\n");ch = getchar();//接收输入while(getchar() != '\n')//清空缓冲区{continue;}return ch;//返回输入选项,启动相关函数调用
}ElemType Input()
{ElemType p; //定义个结构体变量,用于初始化调用此函数时的成员信息printf("成员姓名:");gets(p.name); //接收姓名printf("出生日期:");gets(p.bothDay); //接收出生日期printf("成员住址:");gets(p.address); //接收住址printf("是否结婚(0/1):"); //0代表未婚,1代表已婚scanf("%d",&p.getMatings); //接收是否结婚getchar();printf("是否健在(0/1):");//0代表死亡,1代表健在scanf("%d",&p.keepAlive); //接收是否健在 getchar();if(p.keepAlive == 0) //若死亡,接收死亡日期{printf("死亡日期:");gets(p.deathDay); }return p; //返回结构体变量,初始化此成员的基本个人信息
}void Init(CTree *tree) //初始化
{printf("请确定初始化家谱信息需要的成员数量:");scanf("%d",&tree->n); //接收初始化的时候的成员数printf("请依次输入各个人的信息:\n\n");tree->r = 0; //根结点在数组中的位置!!!for(int i=0; i<tree->n; i++) //循环完善每个成员的信息,包括其孩子和父亲{printf("***********\t正在完善第%d个成员的信息:\t***********\n",i+1);// printf("正在完善第%d个人的信息:\n",i+1);fflush(stdin); //刷新缓冲区tree->nodes[i].data = Input(); //调用Input()函数,初始化此成员信息 tree->nodes[i].firstchild = NULL; //初始化此成员的孩子域为NULLtree->nodes[i].parent = -1; //初始化此成员的父亲在数组中的位置为-1,即为祖先Add_Child(tree, i); //调用初始化此成员的孩子信息Add_Parent_Init(tree, i); //调用函数初始化此成员的父亲信息printf("**********************************************\n");}
}void show_seniority(CTree *tree, int label) //label为此人在数组中的位置
{int book[MAX_TREE_SIZE] = {0}; //存入数组中每个成员的辈分int flag; //标记成员的父亲在数组中的下标int cnt = 0; //根据cnt的值得出此成员的辈分for (int i = 0; i < tree->n; i++) //用迭代替代递归实现,遍历树形结构的家谱普{flag = tree->nodes[i].parent; while(flag != -1) //如果还没有到祖先节点,接继续执行循环体{flag = tree->nodes[flag].parent;cnt++;}book[i] = cnt+1; //第i个成员的辈分cnt = 0; }printf("此人所在辈分是:%d\n",book[label]);
}Status Exist_Name(CTree *tree) //以姓名查询是否存在此人
{int cnt = 0; //统计此人孩子的个数int flag; //得到这个人的此时此刻查询的孩子在数组的下标char demo[LEN]; //接收需要查询人的姓名printf("输入你要找的人的名字:");gets(demo); ChildPtr * p = NULL; //输出其孩子信息int book[MAX_TREE_SIZE] = {0}; //防止重复输出相同孩子信息for(int i=0; i<tree->n; i++){if(!strcmp(tree->nodes[i].data.name, demo)) //找到是否存在此人{printf("查询结果:\n");p = tree->nodes[i].firstchild; //指向该成员的孩子域while(p != NULL){flag = p->child; //得到其孩子在数组中的位置if(!book[flag]) //如果这个孩子没有输出过的花,则输出其孩子信息{printf("其第%d个孩子的名字是: ",cnt+1);puts(tree->nodes[flag].data.name); //输出后自动换行book[flag] = 1;cnt++;//统计这个成员的孩子数}p = p->next; //指向下一个孩子}if(cnt == 0) //如果这个孩子数为0{printf("此人目前还没有孩子!\n");}if(-1 == tree->nodes[i].parent) //如果他是祖先的话,则父亲未知{printf("家族祖先,其父亲目前尚未知悉!\n");show_seniority(tree, i); //调用显示其辈分的函数return OK; //返回操作成功}printf("其父亲的名字是: ");puts(tree->nodes[(tree->nodes[i].parent)].data.name);show_seniority(tree, i); //调用显示其辈分的函数return OK;}}printf("查询结果:\n此家谱中没有此人!\n");return ERROR; //如果在数组中没有找到这个人的姓名,返回查询失败ERROR
}Status Exist_BothDay(CTree *tree) //以出生日期判断是否存在此人
{int cnt = 0; //统计孩子数int flag; //得到此节点的孩子在数组的位置int exist = 0; int sum = 0; //统计满足此生日的人数int book[MAX_TREE_SIZE] = {0}; //标记此成员已经是否被输出过char demo[LEN]; //接收输入printf("输入你要找的人的生日:");gets(demo); ChildPtr * p =NULL;printf("查询结果:\n");for(int i=0; i<tree->n; i++) //循环查询满足此生日的成员{if(!strcmp(tree->nodes[i].data.bothDay, demo)) //如果发现有满足这个出生日期的{exist = 1; //标记存在printf("满足此生日的第%d个人是",sum+1);puts(tree->nodes[i].data.name);p = tree->nodes[i].firstchild; //指向此人的孩子域while(p != NULL) //如果他有孩子的话{flag = p->child; //为了防止重复输出,故标记之if(!book[flag]){printf("其第%d个孩子的名字是: ",cnt+1);puts(tree->nodes[flag].data.name); //输出后自动换行book[flag] = 1; //他被输出过,标记为1cnt++; //统计孩子个数}p = p->next; //指向下一个孩子域}if(cnt == 0) //如果这个人没有孩子{printf("此人目前还没有孩子!\n");}if(-1 == tree->nodes[i].parent) //如果他的父亲在数组中的位置为-1,则此人为祖先{printf("家族祖先,其父亲目前尚未知悉!\n");}else{printf("其父亲的名字是: ");puts(tree->nodes[(tree->nodes[i].parent)].data.name);}sum++; //继续查询其他人还有满足此出生日期的show_seniority(tree, i); //调用显示其辈分的函数}cnt = 0; //查询其他人的是否,把统计孩子的变量赋值为0}if(!exist) //如果数组中没有满足此生日的人{printf("此家谱中没有此人!\n");return ERROR; //返回ERROR,查询失败}return OK; //反之,查询操作成功!
}void Inquire(CTree *tree) //查询功能
{int status; //根据返回值反馈操作是否成功int choice; //接收用户的选项while((choice = get_choice_Inquire()) != 'q'){switch (choice){case 'a': status = Exist_Name(tree); //调用按照姓名查询功能if(status) //如果成功查询{printf("查询操作成功!\n");}break;case 'b':status = Exist_BothDay(tree); //调用按照出生日期查询功能if(status) //如果成功查询{printf("查询操作成功!\n");}break;case 'q':default:break;}}}void Add_Child(CTree *tree, int i) //为数组节点增加孩子
{int sum;ChildPtr * ptr = NULL;printf("正在准备为第%d个成员完善->孩子<-信息\n",i+1);fflush(stdin); //刷新缓冲区printf("请输入该成员的孩子数量:");scanf("%d",&sum); //接收该成员的个数getchar(); ///接收换行符号if(sum != 0) {for(int j=0; j<sum; j++) //确定每个孩子在数组中的位置{ptr = (ChildPtr*)malloc(sizeof(ChildPtr));if(ptr == NULL){printf("分配内存失败!程序终止!");exit(-1);}else{printf("请输入第%d个->孩子<-在数组中的<下标>:",j+1);scanf("%d",&ptr->child); //接收该孩子在数组中的下标getchar();ptr->next = tree->nodes[i].firstchild; //是该成员的孩子域指向此孩子的位置tree->nodes[i].firstchild = ptr;//更新下一个孩子的信息ptr = NULL;}}}else{printf("此人目前还没有孩子!\n");}
}void Add_Parent_Init(CTree *tree, int i) //为数组节点确定父节点
{int flag; //接收此成员父亲在数组的下标if(i == tree->r) //数组下标为0,为祖先{tree->nodes[i].parent = -1;}else{fflush(stdin); //刷新缓冲区printf("请输入第%d个节点的->父亲<-在数组中的<下标>:",i+1);scanf("%d",&flag); //接收父亲在数组中的下标getchar();tree->nodes[i].parent = flag;}
}
/*** 新增加的成员其父亲的初始化和刚刚初始化的时候成员其父亲的初始化有不同之处,不能简单的* 像初始化其孩子一样,初始化成员的时候其父亲初始化属于创建单链表,而此时为新增加的成员* 初始化其父亲,相当于单链表的插入操作!*/
void Add_Parent_Person(CTree *tree, int i)
{ChildPtr * ptr = NULL; //同步更新父节点的孩子链表int flag; //此节点父节点所在数组的下标fflush(stdin);printf("请输入第%d个新成员的->父亲<-在数组中的<下标>:",i+1);scanf("%d",&flag); //接收父亲节点在数组中位置getchar();tree->nodes[i].parent = flag; //为此成员的父亲元素填充此父亲节点在数组中的下标ptr = (ChildPtr*)malloc(sizeof(ChildPtr));if(ptr == NULL){printf("分配内存失败!程序终止!");exit(-1);}else{ptr->child = i; //更新父亲节点中孩子的指针域,即为父亲节点的孩子域中添加这个新的成员孩子ptr->next = tree->nodes[flag].firstchild;tree->nodes[flag].firstchild = ptr;}
}
Status Add_Person(CTree *tree)
{int sum; //确定新增加成员的人数int cnt = tree->n; //之前已经存在的人数printf("输入你准备增加的人数:");scanf("%d",&sum);getchar();tree->n += sum; //更新总人数printf("请依次输入各个人的信息:\n");for(int i=0; i<sum; i++) //为每一个新成员完善信息{printf("***********\t正在完善第%d个新成员的信息:\t***********\n",i+1);fflush(stdin); //刷新缓冲区tree->nodes[cnt+i].data = Input(); //调用函数,初始化新增成员的个人基本信息tree->nodes[cnt+i].firstchild = NULL; //tree->nodes[cnt+i].parent = -1;Add_Child(tree, cnt+i);Add_Parent_Person(tree, cnt+i);printf("**************************************************\n");}return OK; //如果成功添加
}Status Remove(CTree *tree) //删除某人
{int cnt = 0;printf("请输入要从家谱中移除的姓名:");int flag; //确定要删除的人在数组中的下标int exist = 0; //判断此人是否在家谱中存在char demo[LEN];//接收要删除人的姓名gets(demo); for(int i=0; i<tree->n; i++){if(!strcmp(tree->nodes[i].data.name, demo)) //判断此数组中有没有要删除的人{flag = i;exist = 1; //标记,说明此数组中存在这个人break;}}if(exist) //如果存在这个人的话{for(int i=flag; i<tree->n; i++){tree->nodes[i] = tree->nodes[i+1]; //让这个人所在数组中后面的人往期移一个位置}tree->n--;return OK; //删除操作成功}return ERROR; //没有找到这个人,删除操作失败
} Status Modify(CTree *tree) //修改某人信息
{int flag = -1; char demo[LEN]; //接收要删除人的姓名printf("输入你要修改的人的名字:");gets(demo); for(int i=0; i<tree->n; i++){if(!strcmp(tree->nodes[i].data.name, demo)) //查找是否存在此人{flag = i; //接收这个人在数组中下标位置break;}}if(flag == -1) //如果数组中没有这个人{return ERROR; //修改操作失败}int choice; //接收选项memset(demo, '0', LEN); //初始化该数组while((choice = get_choice_Modify()) != 'q'){switch (choice){case 'a':printf("请重新编辑此人姓名:");gets(demo);strcpy(tree->nodes[flag].data.name, demo);break;case 'b':printf("请重新编辑此人出生日期:");gets(demo);strcpy(tree->nodes[flag].data.bothDay, demo); //把新的名字赋值给该成员break;case 'c':printf("请重新编辑此人是否健在:");scanf("%d",&tree->nodes[flag].data.keepAlive); //更新此人是否健在状况getchar();if(tree->nodes[flag].data.keepAlive == 0) //如果其死亡{printf("输入死亡日期:");gets(tree->nodes[flag].data.deathDay); //更新此人的死亡日期}break;case 'd':printf("请重新编辑此人编辑是否已婚:");scanf("%d",&tree->nodes[flag].data.getMatings); //更新此人是否已婚getchar();break;case 'q':default:break;}}return OK;
}
/*** 对一个成员数组按照出生日期进行排序,应该慎重的选择排序算法,此处相当于桶排序,因为不能让成员在数组* 中的位置发生变化,否则其孩子将失效,并且也不能单独改变生日在数组中下标,所以此处一些常见的排序算法* 我目前不知如何应用,故采用桶排序远离,去创建一个数组,其下标从小到大顺序存储按照生日排序成员在数组中过的* 下标位置*/
Status Sort_BothDay(CTree *tree) //对家谱里的人进行排序
{int sort[MAX_TREE_SIZE] = {0}; //该数组用于接收排序后的成员的下标值char min_string[MAX_TREE_SIZE] = {'\0'};int min_int;int book[MAX_TREE_SIZE] = {0}; //用于标记已经排好序的成员int i = 0;int cnt = 0; //统计排好序的人数while(i < tree->n) {min_int = i;strcpy(min_string, tree->nodes[i].data.bothDay);while(book[i] != 0){i++; //检索数组下标min_int = i; //假设此时最小成员的数组下标为istrcpy(min_string, tree->nodes[i].data.bothDay); }for(int j=0; j<tree->n; j++){if((book[j]==0)&&(i!=j)&&strcmp(min_string, tree->nodes[j].data.bothDay)>0){min_int = j;strcpy(min_string, tree->nodes[j].data.bothDay);}}sort[cnt++] = min_int;book[min_int] = 1;i = 0;if(cnt == tree->n){break;}}printf("按出生日期进行排序:\n");for (int i = 0; i < tree->n; i++){printf("第%d个人是%s,他的出生日期为:%s\n",i+1, tree->nodes[sort[i]].data.name,tree->nodes[sort[i]].data.bothDay);}return OK; //排序操作成功,返回操作成功!
}void Destroy(CTree *tree)
{ChildPtr * p = NULL;ChildPtr * q = NULL;for (int i = 0; i < tree->n; i++){p = tree->nodes[i].firstchild;q = p;while(p){p = p->next;free(q);q = p;}}
} void Data_write(CTree *tree)
{printf("👇即将把数据存入文本文件中>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>\n");const char *file = "homefamily.txt";ofstream outfile(file, ios::trunc);if(!outfile){printf("文件打开失败!\n");exit(-1); }else{outfile<<"成员姓名"<<"\t"<<"出生日期"<<"\t"<<"家庭地址"<<endl;for (int i = 0; i < tree->n; i++){ outfile<<tree->nodes[i].data.name<<"\t"<<tree->nodes[i].data.bothDay<<"\t"<<tree->nodes[i].data.address<<endl;}outfile.close();printf("程序数据写入文件成功!!\n");}
}
主函数:treeco.cpp
#include "treeheader.h"
int main()
{CTree ctree;User_login(&ctree); //用户登录函数return 0;
}
运行示例:
➜ TreeDemo g++ implements.cpp treeco.cpp -o Tree
➜ TreeDemo ./Tree
*********** 欢迎登陆家族管理系统 ***********
warning: this program uses gets(), which is unsafe.
输入您的用户名:user_super
请输入管理员密码:123123欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
a
请确定初始化家谱信息需要的成员数量:4
请依次输入各个人的信息:*********** 正在完善第1个成员的信息: ***********
成员姓名:jia
出生日期:19991005
成员住址:nanjing
是否结婚(0/1):0
是否健在(0/1):1
正在准备为第1个成员完善->孩子<-信息
请输入该成员的孩子数量:2
请输入第1个->孩子<-在数组中的<下标>:1
请输入第2个->孩子<-在数组中的<下标>:2
**********************************************
*********** 正在完善第2个成员的信息: ***********
成员姓名:yi
出生日期:19960405
成员住址:chengdu
是否结婚(0/1):1
是否健在(0/1):1
正在准备为第2个成员完善->孩子<-信息
请输入该成员的孩子数量:1
请输入第1个->孩子<-在数组中的<下标>:3
请输入第2个节点的->父亲<-在数组中的<下标>:0
**********************************************
*********** 正在完善第3个成员的信息: ***********
成员姓名:bing
出生日期:20040503
成员住址:beijing
是否结婚(0/1):1
是否健在(0/1):1
正在准备为第3个成员完善->孩子<-信息
请输入该成员的孩子数量:0
此人目前还没有孩子!
请输入第3个节点的->父亲<-在数组中的<下标>:0
**********************************************
*********** 正在完善第4个成员的信息: ***********
成员姓名:ding
出生日期:19991005
成员住址:shanghai
是否结婚(0/1):0
是否健在(0/1):1
正在准备为第4个成员完善->孩子<-信息
请输入该成员的孩子数量:0
此人目前还没有孩子!
请输入第4个节点的->父亲<-在数组中的<下标>:1
**********************************************欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
f
按出生日期进行排序:
第1个人是yi,他的出生日期为:19960405
第2个人是jia,他的出生日期为:19991005
第3个人是ding,他的出生日期为:19991005
第4个人是bing,他的出生日期为:20040503
排序操作成功!欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
c
输入你准备增加的人数:2
请依次输入各个人的信息:
*********** 正在完善第1个新成员的信息: ***********
成员姓名:wu
出生日期:20050401
成员住址:chongqing
是否结婚(0/1):1
是否健在(0/1):1
正在准备为第5个成员完善->孩子<-信息
请输入该成员的孩子数量:1
请输入第1个->孩子<-在数组中的<下标>:3
请输入第5个新成员的->父亲<-在数组中的<下标>:1
**************************************************
*********** 正在完善第2个新成员的信息: ***********
成员姓名:hua
出生日期:20050401
成员住址:suzhou
是否结婚(0/1):1
是否健在(0/1):1
正在准备为第6个成员完善->孩子<-信息
请输入该成员的孩子数量:1
请输入第1个->孩子<-在数组中的<下标>:6
请输入第6个新成员的->父亲<-在数组中的<下标>:-1
**************************************************
添加新成员成功!欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
h
👇即将把数据存入文本文件中>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
程序数据写入文件成功!!欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
c
输入你准备增加的人数:2
请依次输入各个人的信息:
*********** 正在完善第1个新成员的信息: ***********
成员姓名:cao
出生日期:20060504
成员住址:nantong
是否结婚(0/1):1
是否健在(0/1):1
正在准备为第7个成员完善->孩子<-信息
请输入该成员的孩子数量:0
此人目前还没有孩子!
请输入第7个新成员的->父亲<-在数组中的<下标>:5
**************************************************
*********** 正在完善第2个新成员的信息: ***********
成员姓名:shu
出生日期:20040504
成员住址:xuzhou
是否结婚(0/1):1
是否健在(0/1):1
正在准备为第8个成员完善->孩子<-信息
请输入该成员的孩子数量:0
此人目前还没有孩子!
请输入第8个新成员的->父亲<-在数组中的<下标>:-1
**************************************************
添加新成员成功!欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
h
👇即将把数据存入文本文件中>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
程序数据写入文件成功!!欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
e
输入你要修改的人的名字:ding
欢迎使用此家族管理系统的修改系统!!!
a. 编辑姓名 b. 编辑出生日期
c. 编辑是否健在 d. 编辑是否已婚
a
请重新编辑此人姓名:xiaoming
欢迎使用此家族管理系统的修改系统!!!
a. 编辑姓名 b. 编辑出生日期
c. 编辑是否健在 d. 编辑是否已婚
q
修改此人操作成功!欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
h
👇即将把数据存入文本文件中>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
程序数据写入文件成功!!欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
d
请输入要从家谱中移除的姓名:shu
删除此人操作成功!欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
h
👇即将把数据存入文本文件中>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
程序数据写入文件成功!!欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
g欢迎使用此家族管理系统!!!
*************************************
Enter the letter of your choice:
a. 初始化家族谱 b. 查询信息
c. 增加新成员 d. 删除成员
e. 修改成员 f. 按生日进行排序
g. 释放内存 h. 存入文本文件
**************q. 退出程序***********
q
图片