目录
1.test.c
2.contatc.h
3.contact.c
4.总结
一、test.c
#define _CRT_SECURE_NO_WARNINGS 1
//练习:——完成
//通讯录——VS项目——Contact(通讯录)
//
//需求:
//1.能够存放1000个人的信息
//信息包含:年龄、名字、性别、电话、地址、电子邮件、职业
//2.增加联系人
//3.删除联系人
//4.修改联系人信息
//5.查找联系人信息
//6.排序通讯录的信息
// 7.显示打印信息
// 8.退出程序
//
//实现思路:
//contact.h——类型的定义,函数的声明
//contact.c——函数的实现
//test.c——测试模块
#include "contact.h"
void menu()
{
printf("*****************************************\n");
printf("********* 通讯录管理系统 **********\n");
printf("*****************************************\n");
printf("******* 0.exit *******\n");
printf("******* 1.add 2.del *******\n");
printf("******* 3.search 4.revise *******\n");
printf("******* 5.sort 6.print *******\n");
printf("******* 7.cls 8.del all *****\n");
printf("*****************************************\n");
printf("*****************************************\n");
}
enum op
{
EXIT,
ADD,
DEL,
SEARCH,
REVISE,
SORT,
PRINT,
CLS,
DELALL
};
//在栈上开辟的空间太大了,动态内存开辟学完之后记得转移到堆上面
//已改造——动态增长
//学习完文件之后记得把数据存储到数据库或文件中
//已修改
int main()
{
int input = 0;
//创建通讯录
Contact con;
//初始化通讯录——加载文件
//将使用动态内存开辟技术进行初始化
Initcontact(&con);
do
{
menu();
printf("请选择:\n");
scanf("%d", &input);
switch (input)
{
case ADD:
//添加联系人
ADD_PEOPLE(&con);//修改,增容
break;
case DEL:
//删除联系人
bekghDEL_PEOPLE(&con);
break;
case SEARCH:
//查找联系人
SEARCH_PEOPLE(&con);
break;
case REVISE:
//修改联系人
REVISE_PEOPLE(&con);
break;
case SORT:
//排序联系人
SORT_PEOPLE(&con);
break;
case PRINT:
//打印联系人
PRINT_PEOPLE(&con);
break;
case EXIT:
//保存信息到文件
Save_Contct(&con);
//销毁通讯录
Destory_Contact(&con);
//退出程序
printf("退出程序\n");//修改,动态释放
break;
case CLS:
//清屏
system("cls");
break;
case DELALL:
//删除所有联系人
DEL_Contact(&con);
break;
default:
printf("选择错误,请重新选择\n");
break;
}
} while (input);
return 0;
}
二、contact.h
#define _CRT_SECURE_NO_WARNINGS 1
#pragma once
//包含的头文件
#include
#include
#include
//类型的定义
//
//定义联系人信息
//#define MAX_NUM 1000//静态
#define MAX_NAME 20
#define MAX_SEX 10
#define MAX_AGE 10
#define MAX_NUMBER 12
#define MAX_ADDR 30
#define MAX_SZ 3//起始最大容量
#define DEFAULT_SZ 2//默认增长容量
typedef struct contact_informationn
{
char name[MAX_NAME];
char sex[MAX_SEX];
int age[MAX_AGE];
char number[MAX_NUMBER];
char addr[MAX_ADDR];
}contact_informationn;
//静态版本
//typedef struct Contact
//{
// contact_informationn data[MAX_NUM];//存放联系人信息
// int sz;//记录通讯录的有效联系人个数
//}Contact;
//动态版本
typedef struct Contact
{
contact_informationn* data;//指向动态申请的空间,用来存放联系人信息
int sz;//记录通讯录的有效联系人个数
int capacity;//记录当前通讯录的最大容量
}Contact;
//函数的声明
//
//初始化通讯录
void Initcontact(Contact* pc);
//添加联系人
void ADD_PEOPLE(Contact* pc);
//打印联系人
void PRINT_PEOPLE(const Contact* pc);
//删除联系人
void bekghDEL_PEOPLE(Contact* pc);
//查找联系人
void SEARCH_PEOPLE(const Contact* pc);
//修改联系人
void REVISE_PEOPLE(Contact* pc);
//排序联系人
void SORT_PEOPLE(const Contact* pc);
//销毁通讯录
void Destory_Contact(Contact* pc);
//保存信息到文件
void Save_Contct(Contact* pc);
//加载文件
void Load_Contact(Contact* pc);
//考虑增容问题
void cheak_contact(Contact* pc);
//删除所有联系人
void DEL_Contact(Contact* pc);
三、contact.c
#define _CRT_SECURE_NO_WARNINGS 1
#include "contact.h"
int count = 0;//存储联系人个数
初始化通讯录——静态版本
//void Initcontact(Contact* pc)
//{
// pc->sz = 0;
// memset(pc->data, 0, sizeof(pc->data));
//}
//加载文件
void Load_Contact(Contact* pc)
{
//打开文件
FILE* p = fopen("Contact.txt", "r");
if (p == NULL)
{
perror("Load_Contact");
return;
}
//读文件
contact_informationn tmp = { 0 };
while (fread(&tmp, sizeof(contact_informationn), 1,p ))
{
//判断是否需要增容
cheak_contact(pc);
pc->data[pc->sz] = tmp;
pc->sz++;
count++;
}
//关闭文件
fclose(p);
p = NULL;
}
//初始化通讯录——动态版本
void Initcontact(Contact* pc)
{
pc->data = (contact_informationn*)malloc(DEFAULT_SZ * sizeof(contact_informationn));
if (pc->data == NULL)
{
perror("Initcontact");
return;
}
pc->sz = 0;//初始化后默认为0
pc->capacity = DEFAULT_SZ;
//加载文件
Load_Contact(pc);
}
//静态版本
//添加联系人
//void ADD_PEOPLE(Contact* pc)
//{
// //判断通讯录是否存满
// if (pc->sz == MAX_NUM)
// {
// printf("通讯录已满,添加失败\n");
// return;
// }
//
// //增加一个联系人
// printf("请输入姓名\n");
// scanf("%s", pc->data[pc->sz].name);
// printf("请年龄\n");
// scanf("%s", &(pc->data[pc->sz].age));
// printf("请输入性别\n");
// scanf("%s", pc->data[pc->sz].sex);
// printf("请输入手机号码\n");
// scanf("%s", pc->data[pc->sz].number);
// printf("请输入住址\n");
// scanf ("%s", pc->data[pc->sz].addr);
//
// pc->sz++;
// printf("添加成功\n");
//}
void cheak_contact(Contact* pc)
{
//判断通讯录是否存满
if (pc->sz == pc->capacity)
{
//增容
contact_informationn* ptr = (contact_informationn*)realloc(pc->data, (pc->capacity + DEFAULT_SZ) * sizeof(contact_informationn));
if (ptr == NULL)
{
//增容失败
perror("ADD_PEOPLE");
printf("增加联系人失败\n");
return;
}
else
{
//增容成功
pc->data = ptr;
pc->capacity += DEFAULT_SZ;
printf("增容成功\n");//方便观察动态内存是否进行自增容
}
}
}
//动态版本
void ADD_PEOPLE(Contact* pc)
{
cheak_contact(pc);
//增加一个联系人
printf("请输入姓名\n");
scanf("%s", pc->data[pc->sz].name);
printf("请年龄\n");
scanf("%s", &(pc->data[pc->sz].age));
printf("请输入性别\n");
scanf("%s", pc->data[pc->sz].sex);
printf("请输入手机号码\n");
scanf("%s", pc->data[pc->sz].number);
printf("请输入住址\n");
scanf("%s", pc->data[pc->sz].addr);
pc->sz++;
printf("添加成功\n");
count++;
}
//打印联系人
void PRINT_PEOPLE(const Contact* pc)
{
if (pc->sz == 0)
{
printf("通讯录为空\n");
}
//打印人数
printf("联系人个数:%d\n", count);
//打印标题
printf("%-20s\t%-5s\t%-5s\t%-12s\t%-20s\n", "名字", "年龄", "性别", "电话", "地址");
//打印数据
for (int i = 0; i < pc->sz; i++)
{
printf("%-20s\t%-5s\t%-5s\t%-12s\t%-20s\n",
pc->data[i].name,
pc->data[i].age,
pc->data[i].sex,
pc->data[i].number,
pc->data[i].addr);
}
}
//通过姓名查找
static int Find_By_Name(Contact* pc, char name[])
{
for (int i = 0; i < pc->sz; i++)
{
if (strcmp(pc->data[i].name, name) == 0)
{
//找到了
return i;
}
}
//找不到
return -1;
}
//删除联系人
void bekghDEL_PEOPLE(Contact* pc)
{
//判断通讯录联系人数量是否为空
if (pc->sz == 0)
{
printf("通讯录已空,无需删除\n");
return;
}
char name[MAX_NAME];
printf("请输入要删除的联系人的姓名\n");
scanf("%s", name);
//查找该联系人是否有要删除的联系人
int pos = Find_By_Name(pc,name);
//没有——停止操作
if (pos == -1)
{
printf("通讯录没有该联系人,请核实后在进行该操作\n");
return;
}
//有——删除
for (int i = pos; i < pc->sz - 1; i++)
{
pc->data[i] = pc->data[i + 1];
}
pc->sz--;
count--;
printf("删除成功\n");
}
//查找联系人
void SEARCH_PEOPLE(const Contact* pc)
{
if (pc->sz == 0)
{
printf("通讯录已空,无需查找\n");
return;
}
char name[MAX_NAME];
printf("请输入要查找的联系人的姓名\n");
scanf("%s", name);
//查找该联系人是否有要查找的联系人
int pos = Find_By_Name(pc, name);
//没有——停止操作
if (pos == -1)
{
printf("通讯录没有该联系人,请核实后在进行该操作\n");
return;
}
//有
else
{
printf("%-20s\t%-5s\t%-5s\t%-12s\t%-20s\n", "名字", "年龄", "性别", "电话", "地址");
printf("%-20s\t%-5s\t%-5s\t%-12s\t%-20s\n",
pc->data[pos].name,
pc->data[pos].age,
pc->data[pos].sex,
pc->data[pos].number,
pc->data[pos].addr);
}
}
//修改联系人
void REVISE_PEOPLE(Contact* pc)
{
if (pc->sz == 0)
{
printf("通讯录已空,无需修改\n");
return;
}
char name[MAX_NAME];
printf("请输入要修改的联系人的姓名\n");
scanf("%s", name);
//查找该联系人是否有要修改的联系人
int pos = Find_By_Name(pc, name);
//没有——停止操作
if (pos == -1)
{
printf("通讯录没有该联系人,请核实后在进行该操作\n");
return;
}
//有
else
{
//修改一个联系人
printf("请输入姓名\n");
scanf("%s", pc->data[pos].name);
printf("请年龄\n");
scanf("%s", &(pc->data[pos].age));
printf("请输入性别\n");
scanf("%s", pc->data[pos].sex);
printf("请输入手机号码\n");
scanf("%s", pc->data[pos].number);
printf("请输入住址\n");
scanf("%s", pc->data[pos].addr);
printf("修改成功\n");
}
}
//排序联系人_未完成
//void Menu()
//{
// printf("*****************************************\n");
// printf("****** 1. name 2. age *******\n");
// printf("*****************************************\n");
//}
//
//int char_cmp(const void* p1, const void* p2)
//{
// return strcmp(((contact_informationn*)p1)->name, ((contact_informationn *)p2)->name);
//}
//int int_cmp(const void* p1, const void* p2)
//{
// return ((contact_informationn*)p1)->age - (( contact_informationn*)p2)->age;
//}
//
//void SORT_PEOPLE(const Contact* pc)
//{
//
// int input;
// do
// {
// Menu();
// printf("请输入按照什么要求排序:>");
// scanf("%d", &input);
// switch (input)
// {
// case 1:
// //qsort(pc->data->name, pc->size, sizeof(struct PeoInfo), char_cmp);
// qsort(pc->data, pc->sz, sizeof(contact_informationn), char_cmp);//进行排序
// printf("成功按照姓名进行排序~!\n");
// input = 0;
// break;
// case 2:
// qsort(pc->data, pc->sz, sizeof(contact_informationn), int_cmp);//进行排序
// printf("成功按照年龄进行排序~!\n");
// input = 0;
// break;
// default:
// printf("输入错误,请重新输入~!\n");
// break;
// }
// } while (input);
// }
//排序——已完成
int compar1(const void* a, const void* b)
{
return strcmp(((contact_informationn*)a)->name, ((contact_informationn*)b)->name);
}
int compar2(const void* a, const void* b)
{
return ((contact_informationn*)b)->age - ((contact_informationn*)a)->age;
}
void SORT_PEOPLE(Contact* pc)
{
int input = 0;
do
{
printf("请选择要排序的类型:\n");
printf("1.名字大小排序 2.年龄大小排序 0.退出排序\n");
scanf("%d", &input);
switch (input)
{
case 1:
qsort(pc->data, pc->sz, sizeof(contact_informationn), compar1);
printf("名字大小排序成功\n");
break;
case 2:
qsort(pc->data, pc->sz, sizeof(contact_informationn), compar2);
printf("年龄大小排序成功\n");
break;
case 0:
printf("退出排序\n");
break;
default:
printf("选择错误,请重新选择\n");
break;
}
break;
} while (input);
}
//销毁通讯录
void Destory_Contact(Contact* pc)
{
free(pc->data);
pc->data = NULL;
pc->sz = 0;
pc->capacity = 0;
printf("信息已保存\n");//便于测试
}
//保存信息到文件
void Save_Contct(Contact* pc)
{
//打开文件
FILE* p = fopen("Contact.txt", "w");
if (p == NULL)
{
perror("Save_Contct");
return;
}
//写文件
int i = 0;
for (i = 0; i < pc->sz; i++)
{
fwrite(pc->data + i, sizeof(contact_informationn), 1, p);
}
//关闭文件
fclose(p);
p = NULL;
}
//删除所有联系人
void DEL_Contact(Contact* pc)
{
//参照单个删除但无需查找姓名,增加警示询问。
//判断通讯录联系人数量是否为空
if (pc->sz == 0)
{
printf("通讯录已空,无需删除\n");
return;
}
//警示
int tmp = 0;
printf("确定要清空所有联系人吗?\n");
printf("1.yes 2.no\n");
scanf("%d", &tmp);
if (tmp == 1)
{
//删除
pc->data = 0;
pc->sz = 0;
printf("删除成功\n");
count = 0;
}
else
{
printf("已撤销删除\n");
}
}
四、总结
其实这个小项目让我做了一天才搞出来,归根结底还是太菜了,但我想说的是咱并不会效率低就放弃编程的兴趣,我坚信有努力不一定会有收获,但不努力一定不会有收获,加油奥利给!!!