中国山东网站建设,中国企业商铺网,网站的备案all,wordpress首页加外链C语言实现通讯录 #x1f340;实现一个通讯录#xff1a;#x1f340;通讯录的功能#xff1a;#x1f340;多文件实现#x1f4ae;设计结构体——保存人的信息#x1f4ae;初始通讯录#x1f4ae;封装通讯录#x1f4ae;define宏定义修改通讯录的最大容量初始化通讯录… C语言实现通讯录 实现一个通讯录通讯录的功能多文件实现设计结构体——保存人的信息初始通讯录封装通讯录define宏定义修改通讯录的最大容量初始化通讯录大致框架改进--枚举 提高代码的可读性定义函数实现功能AddContactShowContactDelContact进一步改进SearchContactModifyContactSort Contact 完整代码 实现一个通讯录 通讯录中保存人的信息 名字 年龄 性别 电话 住址 通讯录的功能 1.通讯录可以存放100个人的信息 2.显示所有联系人的信息 3.排序功能 4.增增加联系人 5.删删除指定联系人 6.查查找指定联系人 7.改修改指定联系人 多文件实现 test.c 测试通讯录 contact.h 函数和类型的声明 contact.c 函数的实现 设计结构体——保存人的信息
初级
struct PeoInfo
{char name[20];int age;char sex[5];//一个汉字占两个字符char tele[12];char addr[30];
};结构体的引用
struct PeoInfo num1 ;
struct PeoInfo num2;
struct PeoInfo data[50];改进 考虑到每次使用结构体都需要写 struct PeoInfo比较繁琐能不能直接把struct自己省略掉呢 这时候就需要对改结构体进行重命名typedef
typedef struct PeoInfo
{char name[20];int age;char sex[5];char tele[12];char addr[30];
}PeoInfo;这样当我们使用结构体时就不用用 struct PeoInfo了直接使用PeoInfo就可以了。
初始通讯录
因为我们刚刚定义了结构体用来存储人的信息但一个通讯录中有很多人我们上面设置了该通讯录可以存放100个人的信息所以我们需要用结构体数组将每一个类型都是结构体的元素存储起来。 C语言定义结构体数组一般形式
结构体类型 数组名[数组长度];所以我们定义 通讯录
PeoInfo data[100];同时我们需要一个变量来判断通讯录里已经存放数据的个数。(以防止在增添联系人时超过了定义的通讯录的最大容量)
int sz0;封装通讯录
在上面考虑到通讯录PeoInfo data[100]和变量 sz是一种封锁的关系。即sz等于几PeoInfo data里面就有几个数据元素。sz加1则PeoInfo data数组里会再存放一个元素。 所以我们考虑将通讯录进行进一步的封装构建一个结构体
typedef struct Contact
{PeoInfo data[100];int sz;
}Contact;这时我们的通讯录就为 con
Contact con;define宏定义修改通讯录的最大容量 同样我们也可以对 我们刚开始定义的 姓名、地址、联系方式等 以同样的宏定义进行转变。
初始化通讯录
将通讯录初始化为0。可以定义一个函数用来初始化通讯录。
void InitContact(Contact* pc)
{memset(pc-data, 0, sizeof(pc-data);pc-sz 0;
}因为我们要改变通讯录的内部所以函数参数是一个地址值类型是我们定义的通讯录结构体 Contact类型。 利用memset函数将结构体中数组所有元素全部赋值为0.同时将pc所指向的sz也初始化为0.
void InitContact(Contact* pc)
{memset(pc-data, 0, sizeof(pc-data);pc-sz 0;
}大致框架
接下来我们在void test ()函数中写一下大概的框架 因为要尽可能避免在主函数中太过冗长所以我们把通讯录的具体实现——增删查找等等都放在test函数中之后我们就只需要在主函数中进行调用即可。
首先我们可以用do...while循环 打印一个菜单。 定义一个函数 void menu()完成打印。在()函数中调用即可。 之后我们利用switch对输入的input进行判断进行相应的操作。对于下面的七种情况我们可以写七个函数分别实现其相应的功能。 我们进行的所有操作都是对于通讯录而言的所以在test函数中必须有通讯录。所以我们将我们已经初始化的通讯录放在函数中。 不要忘了包含头文件contact.h (在contact.h头文件中包含着本身已经封装好的常见的头文件 比如 stdio.h、string.h等还有我们自己对于结构体或者函数的一些声明和定义比如定义人的信息的结构体 PeoInfo、定义通讯录的 Contact,以及我们函数的声明完成Contact初始化的函数InitContact等还有之后我们要对通讯录进行操作的一系列增删查找函数等函数的声明都会放在都文件中。) 要注意函数的定义不是放在头文件中的而是在contat.c中 改进–枚举 提高代码的可读性 定义函数实现功能
AddContact //增加联系人的信息
void AddContact(Contact* pc)
{//判断数组是否可以增添?if (pc-sz 100){printf(通讯录已满无法添加\n);return;}//通讯录没满else{printf(请输入名字);scanf(%s, pc-data[pc-sz].name);//pc-data 指向的是结构体数组 数组名本身就是地址不用用取地址符号printf(请输入年龄:);scanf(%d, (pc-data[pc-sz].age));printf(请输入性别:);scanf(%s, pc-data[pc-sz].sex);printf(请输入电话:);scanf(%s, pc-data[pc-sz].tele);printf(请输入住址);scanf(%s, pc-data[pc-sz].addr);pc-sz;printf(增加联系人成功);}
}ShowContact //显示所有联系人的信息
void ShowContact(const Contact* pc)//仅仅是显示而不修改 所以用const限制修饰
{int i;for (i 0; i pc-sz; i){printf(姓名%-20s\t, pc-data[i].name);//根据联系人结构体信息printf(年龄%-4d\t, pc-data[i].age);printf(性别:%-5s\t, pc-data[i].sex);printf(电话:%-12s\t, pc-data[i].tele);printf(住址%-13s\t, pc-data[i].addr);//统一左对齐printf(\n);}
}但是当显示的数据变多的时候尽管是左对齐还是不够美观。 接下来我们采用打印标题的形式更好的打印出数据。
//显示所有联系人的信息
void ShowContact(const Contact* pc)//仅仅是显示而不修改 所以用const限制修饰
{int i;//打印列标题printf(%-20s\t%-4s\t%-5s\t%-12s\t%-30s\n, 名字, 年龄, 性别, 电话, 地址);//打印数据for (i 0; i pc-sz; i){printf(%-20s\t%-4d\t%-5s\t%-12s\t%-30s\t\n,pc-data[i].name,pc-data[i].age,pc-data[i].sex,pc-data[i].tele,pc-data[i].addr);}
}DelContact //删除指定联系人
void DelContact(Contact* pc)
{int i 0;char name[20];int pos 0;int flag 0;//输入要删除的人删除printf(请输入要删除人的名字:);scanf(%s, name);//将要删除的人的名字放入name中(name本就是一个地址值)//查找有没有这个人for (i 0; i pc-sz; i ){if (strcmp(name, pc-data[i].name) 0) //字符串比较函数{pos i;//找到了记下位置flag 1;} }if (flag 0){printf(要删除的人不存在\n);return;}//进行删除for (i pos; i pc-sz-1; i){pc-data[i] pc-data[i 1];}pc-sz--;printf(成功删除联系人);
}进一步改进
当我们写后面的函数时我们发现后面的查找函数 还是 修改函数 都需要像 删除函数一样 先在通讯录类进行查找。 为了更高效完成整个工程提高效率我们可以来写一个通过名字进行查找的函数FindByName。 当我们写 删除 查找 修改函数时首先可以直接调用这个函数。
int FindByName(Contact* pc, char name[])
{int flag 0;int i 0;int pos;for (i 0; i pc-sz; i){if (strcmp(name, pc-data[i].name) 0) //字符串比较函数{pos i;//找到了记下位置return pos;}}if (flag 0){printf(要删除的人不存在\n);return -1;}}DelContact函数改进为
//删除指定联系人
void DelContact(Contact* pc)
{int i 0;char name[20];int pos 0;int flag 0;//输入要删除的人删除printf(请输入要删除人的名字:);scanf(%s, name);//将要删除的人的名字放入name中(name本就是一个地址值)//查找有没有这个人if ((FindByName(pc, name) -1)){printf(找不到要删除的联系人);}elsepos FindByName(pc, name); //记下位置//进行删除for (i pos; i pc-sz-1; i){pc-data[i] pc-data[i 1];}pc-sz--;printf(成功删除联系人);
}
SearchContact //查找指定联系人
void SearchContact(const Contact* pc)
{int pos 0;char name[20] { 0 };printf(请输入要查找人的名字:);scanf(%s, name);//查找有没有指定联系人if (FindByName(pc, name) -1)printf(没有找到要查找的联系人\n);else{pos FindByName(pc, name);printf(找到了!\n);printf(该联系人的下标为%d, pos);//打印数据printf(%-20s\t%-4s\t%-5s\t%-12s\t%-30s\n, 名字, 年龄, 性别, 电话, 地址);printf(%-20s\t%-4d\t%-5s\t%-12s\t%-30s\t\n,pc-data[pos].name,pc-data[pos].age,pc-data[pos].sex,pc-data[pos].tele,pc-data[pos].addr);}
}ModifyContact //修改指定联系人
void ModifyContact(Contact* pc)
{int pos 0;char name[20] { 0 };printf(请输入要查找人的名字:);scanf(%s, name);//查找有没有要修改的联系人if (FindByName(pc, name) -1)printf(没有找到要修改的联系人\n);else {printf(找到了要修改的联系人!\n);pos FindByName(pc, name);//修改 修改可以理解为再次录入一遍信息printf(请输入名字);scanf(%s, pc-data[pos].name);printf(请输入年龄:);scanf(%d, (pc-data[pos].age));printf(请输入性别:);scanf(%s, pc-data[pos].sex);printf(请输入电话:);scanf(%s, pc-data[pos].tele);printf(请输入住址);scanf(%s, pc-data[pos].addr);printf(成功修改联系人);}
}Sort Contact //按照名字进行排序
//排序int cmp_name(const void* p1, const void* p2)
{return strcmp(((PeoInfo*)p1)-name, ((PeoInfo*)p2)-name);
}
void SortContact(Contact* pc)
{int i 0;//利用qsort 函数qsort(pc-data, pc-sz, sizeof((pc-data)[0]), cmp_name);//打印列标题printf(%-20s\t%-4s\t%-5s\t%-12s\t%-30s\n, 名字, 年龄, 性别, 电话, 地址);//打印数据for (i 0; i pc-sz; i){printf(%-20s\t%-4d\t%-5s\t%-12s\t%-30s\t\n,pc-data[i].name,pc-data[i].age,pc-data[i].sex,pc-data[i].tele,pc-data[i].addr);}}完整代码
contact.h
#define _CRT_SECURE_NO_WARNINGS 1
#include stdio.h
#include string.h
#define MAX 100//声明结构体--保存人的信息
typedef struct PeoInfo
{char name[20];int age;char sex[5];//一个汉字占两个字符char tele[12];char addr[30];
}PeoInfo;
//声明结构体通讯录
typedef struct Contact
{PeoInfo data[MAX];int sz;
}Contact;
int FindByName(Contact* pc, char name[]);
void AddContact(Contact* pc);
void ShowContact(const Contact* pc);
void DelContact(Contact* pc);
void SearchContact( Contact* pc);
void SearchContact(Contact* pc);
void SortContact(Contact* pc);enum OPTION
{EXIT,//0ADD,//1DEL,//2SEARCH,//3MODIFY,//4SHOW,//5SORT//6
};//函数的声明--初始化通讯录
void InitContact(Contact* pc);contact.c
#include contact.hvoid InitContact(Contact* pc)
{memset(pc-data, 0, sizeof(pc-data));pc-sz 0;
}//增加联系人的信息
void AddContact(Contact* pc)
{//判断数组是否可以增添?if (pc-sz 100){printf(通讯录已满无法添加\n);return;}//通讯录没满else{printf(请输入名字);scanf(%s, pc-data[pc-sz].name);//pc-data 指向的是结构体数组 数组名本身就是地址不用用取地址符号printf(请输入年龄:);scanf(%d, (pc-data[pc-sz].age));printf(请输入性别:);scanf(%s, pc-data[pc-sz].sex);printf(请输入电话:);scanf(%s, pc-data[pc-sz].tele);printf(请输入住址);scanf(%s, pc-data[pc-sz].addr);pc-sz;printf(增加联系人成功);}
}//显示所有联系人的信息
void ShowContact(const Contact* pc)//仅仅是显示而不修改 所以用const限制修饰
{int i;//打印列标题printf(%-20s\t%-4s\t%-5s\t%-12s\t%-30s\n, 名字, 年龄, 性别, 电话, 地址);//打印数据for (i 0; i pc-sz; i){printf(%-20s\t%-4d\t%-5s\t%-12s\t%-30s\t\n,pc-data[i].name,pc-data[i].age,pc-data[i].sex,pc-data[i].tele,pc-data[i].addr);}
}int FindByName(Contact* pc, char name[])
{int flag 0;int i 0;int pos;for (i 0; i pc-sz; i){if (strcmp(name, pc-data[i].name) 0) //字符串比较函数{pos i;//找到了记下位置return pos;}}if (flag 0){printf(要删除的人不存在\n);return -1;}}//删除指定联系人
void DelContact(Contact* pc)
{int i 0;char name[20];int pos 0;int flag 0;//输入要删除的人删除printf(请输入要删除人的名字:);scanf(%s, name);//将要删除的人的名字放入name中(name本就是一个地址值)//查找有没有这个人if ((FindByName(pc, name) -1)){printf(找不到要删除的联系人);}elsepos FindByName(pc, name); //记下位置//进行删除for (i pos; i pc-sz-1; i){pc-data[i] pc-data[i 1];}pc-sz--;printf(成功删除联系人);
}//查找指定联系人
void SearchContact( Contact* pc)
{int pos 0;char name[20] { 0 };printf(请输入要查找人的名字:);scanf(%s, name);//查找有没有指定联系人if (FindByName(pc, name) -1)printf(没有找到要查找的联系人\n);else{pos FindByName(pc, name);printf(找到了!\n);printf(该联系人的下标为%d, pos);//打印数据printf(%-20s\t%-4s\t%-5s\t%-12s\t%-30s\n, 名字, 年龄, 性别, 电话, 地址);printf(%-20s\t%-4d\t%-5s\t%-12s\t%-30s\t\n,pc-data[pos].name,pc-data[pos].age,pc-data[pos].sex,pc-data[pos].tele,pc-data[pos].addr);}
}//修改指定联系人
void ModifyContact(Contact* pc)
{int pos 0;char name[20] { 0 };printf(请输入要查找人的名字:);scanf(%s, name);//查找有没有要修改的联系人if (FindByName(pc, name) -1)printf(没有找到要修改的联系人\n);else {printf(找到了要修改的联系人!\n);pos FindByName(pc, name);//修改 修改可以理解为再次录入一遍信息printf(请输入名字);scanf(%s, pc-data[pos].name);printf(请输入年龄:);scanf(%d, (pc-data[pos].age));printf(请输入性别:);scanf(%s, pc-data[pos].sex);printf(请输入电话:);scanf(%s, pc-data[pos].tele);printf(请输入住址);scanf(%s, pc-data[pos].addr);printf(成功修改联系人);}
}//按照名字进行排序
//排序int cmp_name(const void* p1, const void* p2)
{return strcmp(((PeoInfo*)p1)-name, ((PeoInfo*)p2)-name);
}
void SortContact(Contact* pc)
{int i 0;//利用qsort 函数qsort(pc-data, pc-sz, sizeof((pc-data)[0]), cmp_name);//打印列标题printf(%-20s\t%-4s\t%-5s\t%-12s\t%-30s\n, 名字, 年龄, 性别, 电话, 地址);//打印数据for (i 0; i pc-sz; i){printf(%-20s\t%-4d\t%-5s\t%-12s\t%-30s\t\n,pc-data[i].name,pc-data[i].age,pc-data[i].sex,pc-data[i].tele,pc-data[i].addr);}}test.c #includecontact.hvoid menu()
{printf(\n);printf(******************\n);printf(******请选择******\n);printf(******1.增添******\n);printf(******2.删除******\n);printf(******3.查找******\n);printf(******4.修改******\n);printf(******5.显示******\n);printf(******6.排序******\n);printf(******0.退出******\n);}void test()
{Contact con; //定义结构体变量-通讯录InitContact(con);//对通讯录进行初始化int input 0;do{menu();scanf(%d, input);switch (input){case ADD:AddContact(con);break;case DEL:DelContact(con);break;case SEARCH:SearchContact(con);break;case MODIFY:ModifyContact(con);break;case SHOW:ShowContact(con);break;case SORT:SortContact(con);break;case EXIT:printf(退出通讯录\n);break;default:printf(选择错误重新选择\n);break;}} while (input);}
int main()
{test();return 0;
}