在上个通讯录版本中,运用了事先定义通讯录的大小,再向固定大小的内存里不断的填充每个人的信息,一方面,当我们将开辟的内存用完的时候,将没有办法继续存放信息。另一方面,一般的,我们将通讯录定义的比较大,然而当我们存放的联系人又比较少时,事先开辟的内存又极大的被浪费。因此,他存在很大的缺陷。。。
在这个版本中,为了解决这个问题,运用malloc()和realloc()等用于开辟动态内存的函数。在程序的实现时,先 初始化开辟一个较小的内存用来存放联系人的信息,当内存达上限还需存放信息时,再将原先的内存扩大一些,用于存放要存的联系人,这样需要存放多少联系人就开辟多大的空间。
在实现时,我们不仅关心存放了多少个联系人,更关心通讯录的容量,因此,在上个版本的基础上,我们只需再定义一个保存容量的变量,然后添加容量判断函数,将初始化和最后销毁大小修改即可。
以下,源程序:
1.头文件部分:Contact.h
#ifndef __CONTACT_H__
#define __CONTACT_H__
#define _CRT_SECURE_NO_WARNINGS
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#define NAME_MAX 20
#define SEX_MAX 5
#define TELE_MAX 20
#define ADD_MAX 50
#define INIT_NUM 5 //初始化容量
#define INC_NUM 3 //每次通讯录扩容大小
typedef struct peo
{
char name[NAME_MAX];
char sex[SEX_MAX];
int age;
char tele[TELE_MAX];
char address[ADD_MAX];
}peo;
typedef struct contact
{
peo *arr;
int count;
int capacity;
}contact;
void Add(contact *pcon); //添加联系人
void check_capacity(contact *pcon);//判断容量是否满
void print_contact(contact *pcon);//打印
int find_position(contact *pcon);//查找指定联系人所在位置
int delete_contact(contact *pcon);//删除联系人信息
int find_contacts(contact *pcon);//查找并且输出这个找到的信息。
int revise_contact(contact *pcon);//修改指定联系人的信息
void put_empty(contact *pcon);//清空所有联系人
void sort_name(contact *pcon);//以名字排序所有联系人
void init_contact(contact *pcon);//初始化通讯录
void print_menu();//打印菜单
#endif //_CONTACT_H__
2.函数实现部分:Contact.c
#include "Contact.h"
void print_menu()//打印菜单
{
printf("*******************************************\n");
printf("***** 1.add 2.del 3.clear *****\n");
printf("***** 4.modify 5.show 6.search *****\n");
printf("***** 7.sort 0.exit *****\n");
printf("*******************************************\n");
}
void init_contact(contact *pcon)
{
pcon->count = 0;
pcon->arr = (peo *)malloc(sizeof(peo)*INIT_NUM);
memset(pcon->arr, 0, INIT_NUM*sizeof(peo));
pcon->capacity = INIT_NUM;
}
void check_capacity(contact *pcon) //判断容量是否满
{
if (pcon->count < pcon->capacity)
{
pcon->arr = (peo *)realloc(pcon->arr,sizeof(peo)*INC_NUM);
pcon->capacity = pcon->capacity + INC_NUM;
}
}
void Add(contact *pcon) //添加
{
printf("请输入名字>");
scanf("%s",pcon->arr[pcon->count].name);
printf("请输入性别>");
scanf("%s",pcon->arr[pcon->count].sex);
printf("请输入年龄>");
scanf("%d",&(pcon->arr[pcon->count].age));
printf("请输入电话>");
scanf("%s",pcon->arr[pcon->count].tele);
printf("请输入住址>");
scanf("%s",pcon->arr[pcon->count].address);
pcon->count++;
}
void print_contact(contact *pcon)
{
int i = 0;
for (i=0; i<pcon->count; i++)
{
printf("姓名:%s性别:%s年龄:%d电话:%s地址:%s\n",
pcon->arr[i].name,
pcon->arr[i].sex,
pcon->arr[i].age,
pcon->arr[i].tele,
pcon->arr[i].address);
}
}
int find_position(contact *pcon)//查找指定联系人所在位置
{
int i = 0;
char name[NAME_MAX];
int ret = 0;
printf("请输入名字:");
scanf("%s",name);
for (i=0; i<pcon->count; i++)
{
ret = strcmp(name,pcon->arr[i].name);
if (ret == 0)
{
return i;
}
}
return -1;
}
int delete_contact(contact *pcon)//删除指定联系人信息
{
int i = 0;
int ret = 0;
printf("删除联系人\n");
ret = find_position(pcon);
if (ret == -1)
{
printf("你要删除的姓名不存在!!!\n");
return -1;
}
else
{
for(i=ret; i<pcon->count-1; i++)
{
pcon->arr[i] = pcon->arr[i+1];
}
pcon->count--;
return 0;
}
}
int revise_contact(contact *pcon)//修改指定联系人的信息
{
int ret = 0;
printf("修改联系人信息>");
ret = find_position(pcon);
if (ret == -1)
{
printf("你要修改的联系人不存在!!!\n");
return -1;
}
else
{
printf("请输入要修改的数据:\n");
printf("请输入名字>");
scanf("%s",pcon->arr[ret].name);
printf("请输入性别>");
scanf("%s",pcon->arr[ret].sex);
printf("请输入年龄>");
scanf("%d",&(pcon->arr[ret].age));
printf("请输入电话>");
scanf("%s",pcon->arr[ret].tele);
printf("请输入住址>");
scanf("%s",pcon->arr[ret].address);
return 0;
}
}
void put_empty(contact *pcon)//清空所有联系人(还原成初始化状态)
{
pcon->count = 0;
pcon->arr = (peo *)malloc(sizeof(peo)*INIT_NUM);
memset(pcon->arr, 0, INIT_NUM*sizeof(peo));
pcon->capacity = INIT_NUM;
}
int find_contacts(contact *pcon)//查找并且输出这个找到的信息。
{
int ret = 0;
ret = find_position(pcon);
if (ret == -1)
{
printf("你要查找的名字不存在!!!\n");
return -1;
}
else
{
printf("姓名:%s性别:%s年龄:%d电话:%s地址:%s\n",
pcon->arr[ret].name,
pcon->arr[ret].sex,
pcon->arr[ret].age,
pcon->arr[ret].tele,
pcon->arr[ret].address);
return 0;
}
}
void sort_name(contact *pcon)//以名字排序所有联系人
{
int i = 0;
int j = 0;
int flag = 0;
printf("以名字进行排序(a-->z)\n");
while(1)
{
flag = 0;
for (j = 0; j < pcon->count - 1; j++)
{
if (strcmp(pcon->arr[j].name, pcon->arr[j + 1].name)>0)
{
peo tmp = pcon->arr[j];
pcon->arr[j] = pcon->arr[j + 1];
pcon->arr[j + 1] = tmp;
flag = 1;
}
}
if (flag == 0)
break;
}
}
3.测试部分:test.c
#include "Contact.h"
int main()
{
contact con;
int input = 1;
init_contact(&con);
do
{
print_menu();
printf("请选择>");
scanf("%d",&input);
switch(input)
{
case 1:
Add(&con);
break;
case 2:
delete_contact(&con);
break;
case 3:
put_empty(&con);
break;
case 4:
revise_contact(&con);
break;
case 5:
print_contact(&con);
break;
case 6:
find_contacts(&con);
break;
case 7:
sort_name(&con);
break;
default:
break;
}
} while (input);
return 0;
}