3.5 查找联系人的实现
为了用户方便寻找指定联系人,我们这里封装一个以联系人姓名查找联系人操作,具体如下
void SerchContact(const Contact* pc) { assert(pc); char name[NAME_MAX] = { 0 }; printf("输入要查找人的名字:>"); scanf("%s", name); int pos= Find_by_name(pc, name); if (pos == -1) { printf("要查找的人不存在\n"); return; } printf("%-20s\t%-4s\t%-5s\t%-20s\t%-12s\n", "名字", "年龄", "性别", "地址", "电话"); printf("%-20s\t%-4d\t%-5s\t%-20s\t%-12s\n", pc->data[pos].name, pc->data[pos].age, pc->data[pos].sex, pc->data[pos].addr, pc->data[pos].tele); }
这里由于是利用联系人姓名查找具体的某个联系人,所以还是得利用到上面的函数,这里我们查找到指定联系人后,对联系人信息进行打印,如果没有查找到指定的联系人直接结束函数。
运行展示:
3.6 修改联系人信息
在添加联系人信息时我们很有可能输入错误,那这个时候修改这个功能就显得很重要了,由于修改比较简单,我们就直接给大家上代码
void ModifyContact(Contact* pc) { assert(pc); char name[NAME_MAX] = { 0 }; printf("输入要修改人的名字:>"); scanf("%s", name); int pos = Find_by_name(pc, name); if (pos == -1) { printf("要查找的人不存在\n"); return; } 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].addr); printf("请输入电话:>"); scanf("%s", pc->data[pos].tele); printf("修改完成\n"); }
这里我们直接看运行效果:
3.7 按名字排序联系人
我们给通讯录按名字进行排序,这里我要给大家介绍一个函数qsort函数
qsort函数是基于快速排序的一个排序函数
void qsort (void* base, size_t num, size_t size, int (*compar)(const void*,const void*));
参数介绍:base:指向要排序的数组的第一个对象的指针,转换为 .void*
num:数组中由 指向的元素数。是无符号整型。
size:数组中每个元素的大小(以字节为单位)
compar:该表示的是一个比较函数的函数指针,至于函数指针,等小编给大家介绍指针 的时候介绍,这里我们需要自己构造一个比较函数,该函数的返回值和类型
int compar (const void* p1, const void* p2);
返回值:
这里是根据比较函数的返回值,来给其进行排序方式的。
接下来我给大家演示:
int com(const void* str1, const void* str2) { return strcmp(((peoinfo*)str1)->name, ((peoinfo *)str2)->name); } void SortContact(Contact* pc) { qsort(pc->data, pc->sz, sizeof(pc->data[0]),com); printf("排序成功\n"); }
这里的第一个函数就是比较函数,这里就是排序函数的调用,这里我给大家运行一下
这里就排序完成了。
总代码:
text.c #include<stdio.h> #include "contact.h" void menu() { printf("*************************************\n"); printf("*********1.add 2.del ***********\n"); printf("******** 3.search 4.modify *********\n"); printf("******** 5.show 6.sort ********\n"); printf("********* 0.exit **************\n"); printf("*************************************\n"); } int main() { int input = 0; //创建通讯录 Contact con; //初始化通讯录 InitContact(&con); do { menu(); printf("请选择:>"); scanf("%d", &input); switch (input) { case 1: AddContact(&con); break; case 2: DelContact(&con); break; case 3: SerchContact(&con); break; case 4: ModifyContact(&con); break; case 5: ShowContact(&con); break; case 6: SortContact(&con); break; case 0: printf("退出通讯录\n"); break; default: printf("选择错误\n"); break; } } while (input); return 0; } contact.h #define MAX 1000 #define NAME_MAX 20 #define SEX_MAX 5 #define ADDR_MAX 30 #define TELE_MAX 12 #include <stdlib.h> #include<string.h> #include<stdio.h> #include<assert.h> //人的信息 typedef struct peoinof { char name[NAME_MAX]; int age; char sex[SEX_MAX]; char addr[ADDR_MAX]; char tele[TELE_MAX]; }peoinfo; typedef struct Contact { peoinfo data[MAX];//存放人的信息 int sz;//存放已经存放信息人的个数 }Contact; //初始化通讯录 void InitContact(Contact* pc); //增加联系人 void AddContact(Contact* pc); //显示通讯录的信息 void ShowContact(const Contact* pc); //删除指定联系人 void DelContact(Contact* pc); //查找指定联系人 void SerchContact(Contact* pc); //修改联系人信息 void ModifyContact(Contact* pc); //按名字进行排序 void SortContact(Contact* pc); contact.c #include"contact.h" void InitContact(Contact *pc) { assert(pc); pc->sz = 0; memset(pc->data, 0, sizeof(pc->data));//虽然数组传参传的是数组首地址,但由于这里传的时结构体的地址,所以是 // 可以通过该访问到整个数组的 } void AddContact(Contact* pc) { assert(pc); if (pc->sz == MAX) { printf("通讯录已满,无法添加\n"); return; } printf("请输入名字:>"); scanf("%s", pc->data[pc->sz].name);//由于该是数组名,数组名就是地址,就不需要& printf("请输入年龄:>"); scanf("%d", &pc->data[pc->sz].age); printf("请输入性别:>"); scanf("%s", pc->data[pc->sz].sex); printf("请输入地址:>"); scanf("%s", pc->data[pc->sz].addr); printf("请输入电话:>"); scanf("%s", pc->data[pc->sz].tele); pc->sz++; } void ShowContact(const Contact* pc) { assert(pc); int i = 0; printf("%-20s\t%-4s\t%-5s\t%-20s\t%-12s\n", "名字", "年龄", "性别", "地址", "电话"); for (i = 0; i < pc->sz; i++) { printf("%-20s\t%-4d\t%-5s\t%-20s\t%-12s\n", pc->data[i].name, pc->data[i].age, pc->data[i].sex, pc->data[i].addr, pc->data[i].tele); } } //打印格式前加的数字代表这该类型的数据能打印的个数,正数表示左对齐,负数表示右对齐 int Find_by_name(const Contact* pc,const char* name) { assert(pc && name); int i = 0; for (i = 0; i < pc->sz; i++) { if (strcmp(pc->data[i].name, name) == 0) { return i; } } return - 1; } void DelContact(Contact* pc) { char name[NAME_MAX] = { 0 }; assert(pc); if (pc->sz == 0) { printf("通讯录为空,无法删除\n"); return; } printf("请输入要删除人的名字:>"); scanf("%s", name); int ret=Find_by_name(pc,name); if (ret == -1) { printf("查找的人不存在"); return; } //删除 int i = 0; for (i = ret; i < pc->sz-1; i++) { pc->data[i] = pc->data[i + 1]; } pc->sz--; printf("删除成功\n"); } void SerchContact(const Contact* pc) { assert(pc); char name[NAME_MAX] = { 0 }; printf("输入要查找人的名字:>"); scanf("%s", name); int pos= Find_by_name(pc, name); if (pos == -1) { printf("要查找的人不存在\n"); return; } printf("%-20s\t%-4s\t%-5s\t%-20s\t%-12s\n", "名字", "年龄", "性别", "地址", "电话"); printf("%-20s\t%-4d\t%-5s\t%-20s\t%-12s\n", pc->data[pos].name, pc->data[pos].age, pc->data[pos].sex, pc->data[pos].addr, pc->data[pos].tele); } void ModifyContact(Contact* pc) { assert(pc); char name[NAME_MAX] = { 0 }; printf("输入要修改人的名字:>"); scanf("%s", name); int pos = Find_by_name(pc, name); if (pos == -1) { printf("要查找的人不存在\n"); return; } 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].addr); printf("请输入电话:>"); scanf("%s", pc->data[pos].tele); printf("修改完成\n"); } int com(const void* str1, const void* str2) { return strcmp(((peoinfo*)str1)->name, ((peoinfo *)str2)->name); } void SortContact(Contact* pc) { qsort(pc->data, pc->sz, sizeof(pc->data[0]),com); printf("排序成功\n"); }