单链表和文件操作使用练习:通讯录

1. 项目文件组成(vs2022)

1. Contact.h和Contact.c分别为实现通讯录的头文件和源文件。

2. SList.h和SList.c分别为实现单链表的头文件和源文件。

3. test.c为测试用的源文件,用于调用通讯录提供的函数。

4. Contact.txt用于存储联系人信息。


 

2. 单链表

C语言单链表-CSDN博客 

2.1 头文件

对于该项目,有用的接口就四个。

#pragma once
#include <stdio.h>
#include <stdlib.h>
#include <assert.h>
#include <string.h>
#include "Contact.h"

typedef PeoInfo SLTDataType;

typedef struct SListNode
{
	SLTDataType data;
	struct SListNode* next;
}SLTNode;

//尾插
void SLTPushBack(SLTNode** pphead, SLTDataType x);
//头删
void SLTPopFront(SLTNode** pphead);
//删除pos位置节点
void SLTErase(SLTNode** pphead, SLTNode* pos);
//申请结点
SLTNode* SLTBuyNode(SLTDataType x);

2.2 源文件

#define _CRT_SECURE_NO_WARNINGS
#include "SList.h"

//创建新结点
SLTNode* SLTBuyNode(SLTDataType x)
{
	SLTNode* newnode = (SLTNode*)malloc(sizeof(SLTNode));
	if (newnode == NULL)
	{
		perror("malloc fail!");
		exit(1);
	}
	newnode->data = x;
	newnode->next = NULL;
	return newnode;
}

//尾插
void SLTPushBack(SLTNode** pphead, SLTDataType x)
{
	assert(pphead);
	SLTNode* newnode = SLTBuyNode(x);

	if (*pphead == NULL)
	{
		*pphead = newnode;
	}
	else
	{
		SLTNode* ptail = *pphead;
		while (ptail->next != NULL)
		{
			ptail = ptail->next;
		}
		ptail->next = newnode;
	}
}

//头删
void SLTPopFront(SLTNode** pphead)
{
	assert(pphead && *pphead);
	SLTNode* newphead = (*pphead)->next;
	free(*pphead);
	*pphead = newphead;
}

//删除pos位置节点
void SLTErase(SLTNode** pphead, SLTNode* pos)
{
	assert(pphead && *pphead);
	assert(pos);

	if (pos == *pphead)
	{
		SLTPopFront(pphead);
	}
	else
	{
		SLTNode* prev = *pphead;
		while (prev->next != pos)
		{
			prev = prev->next;
		}
		prev->next = pos->next;
		free(pos);
	}
}

 


3. 通讯录

3.1 头文件

#pragma once
#define NAME_MAX 100
#define SEX_MAX 10
#define TEL_MAX 11
#define ADDR_MAX 100

//前置声明
typedef struct SListNode contact;

//用户数据
typedef struct PersonInfo
{
    char name[NAME_MAX];
    char sex[SEX_MAX];
    int age;
    char tel[TEL_MAX];
    char addr[ADDR_MAX];
}PeoInfo;

//初始化通讯录
void InitContact(contact** con);
//添加通讯录数据
void AddContact(contact** con);
//删除通讯录数据
void DelContact(contact** con);
//展示通讯录数据
void ShowContact(contact* con);
//查找通讯录数据
void FindContact(contact* con);
//修改通讯录数据
void ModifyContact(contact** con);
//销毁通讯录数据
void DestroyContact(contact** con);

3.2 源文件

#define _CRT_SECURE_NO_WARNINGS
#include "Contact.h"
#include "SList.h"

//初始化通讯录
void InitContact(contact** con)
{
	*con = NULL;
	FILE* pf = fopen("Contact.txt", "rb");
	if (pf == NULL)
	{
		perror("fopen");
		exit(-1);
	}
	PeoInfo tmp;
	contact* pcur = *con;
	while (fread(&tmp, sizeof(PeoInfo), 1, pf) == 1)
	{
		if (*con == NULL)
		{
			*con = SLTBuyNode(tmp);
			pcur = *con;
		}
		else
		{
			pcur->next = SLTBuyNode(tmp);
			pcur = pcur->next;
		}
	}
	fclose(pf);
}

//添加通讯录数据
void AddContact(contact** con)
{
	static PeoInfo newpeo;
	printf("请输入新联系人姓名:>");
	scanf("%s", newpeo.name);
	printf("请输入新联系人性别:>");
	scanf("%s", newpeo.sex);
	printf("请输入新联系人年龄:>");
	scanf("%d", &(newpeo.age));
	printf("请输入新联系人电话:>");
	scanf("%s", newpeo.tel);
	printf("请输入新联系人地址:>");
	scanf("%s", newpeo.addr);

	SLTPushBack(con, newpeo);
	printf("添加成功!\n");

	//system("pause"); fflush(stdin); system("cls");
}

//销毁通讯录数据
void DestroyContact(contact** con)
{
	FILE* pf = fopen("Contact.txt", "wb");
	if (pf == NULL)
	{
		perror("fopen");
		exit(-1);
	}
	contact* pcur = *con;
	*con = NULL;
	while (pcur != NULL)
	{
		contact* del = pcur;
		pcur = pcur->next;
		fwrite(del, sizeof(PeoInfo), 1, pf);
		free(del);
		del = NULL;
	}
	fclose(pf);
}

//按名字查找
contact* ConFindByName(contact* con, char* name)
{
	assert(con);
	contact* pcur = con;
	while (pcur != NULL)
	{
		if (strcmp(pcur->data.name, name) == 0)
			return pcur;
		pcur = pcur->next;
	}
	return NULL;
}

//删除通讯录数据
void DelContact(contact** con)
{
	assert(*con);
	char name[NAME_MAX];
	printf("请输入要删除的联系人的姓名:>");
	scanf("%s", name);
	contact* find = ConFindByName(*con, name);
	if (find == NULL)
	{
		printf("查无此人!\n");
	}
	else
	{
		SLTErase(con, find);
		printf("删除成功!\n");
	}
}

//展示通讯录数据
void ShowContact(contact* con)
{
	if (con == NULL)
	{
		printf("暂无联系人!\n");
		return;
	}
	contact* pcur = con;
	printf("%-10s\t%-10s\t%-5s\t%-20s\t%-20s\n", "姓名", "性别", "年龄", "电话", "地址");
	while (pcur != NULL)
	{
		printf("%-10s\t%-10s\t%-5d\t%-20s\t%-20s\n", pcur->data.name, pcur->data.sex, pcur->data.age, pcur->data.tel, pcur->data.addr);
		pcur = pcur->next;
	}
}

//查找通讯录数据
void FindContact(contact* con)
{
	assert(con);
	char name[NAME_MAX];
	printf("请输入要查找的联系人的姓名:>");
	scanf("%s", name);
	contact* find = ConFindByName(con, name);
	if (find == NULL)
	{
		printf("查无此人!\n");
	}
	else
	{
		printf("%-10s\t%-10s\t%-5s\t%-20s\t%-20s\n", "姓名", "性别", "年龄", "电话", "地址");
		printf("%-10s\t%-10s\t%-5d\t%-20s\t%-20s\n", find->data.name, find->data.sex, find->data.age, find->data.tel, find->data.addr);
	}
}

//修改通讯录数据
void ModifyContact(contact** con)
{
	assert(*con);
	char name[NAME_MAX];
	printf("请输入要修改的联系人的姓名:>");
	scanf("%s", name);
	contact* find = ConFindByName(*con, name);
	if (find == NULL)
	{
		printf("查无此人!\n");
	}
	else
	{
		printf("请输入该联系人的新名字:>");
		scanf("%s", find->data.name);
		printf("请输入该联系人的新性别:>");
		scanf("%s", find->data.sex);
		printf("请输入该联系人的新年龄:>");
		scanf("%d", &(find->data.age));
		printf("请输入该联系人的新电话:>");
		scanf("%s", find->data.tel);
		printf("请输入该联系人的新地址:>");
		scanf("%s", find->data.addr);

		printf("修改成功!\n");
	}
}

4. test.c

#define _CRT_SECURE_NO_WARNINGS
#include "Contact.h"
#include "SList.h"

enum options
{
	Exit,
	Add,
	Del,
	Find,
	Modi,
	Show
};

void menu()
{
	printf("||=========通讯录=========||\n");
	printf("||======1.增加联系人======||\n");
	printf("||======2.删除联系人======||\n");
	printf("||======3.查找联系人======||\n");
	printf("||======4.修改联系人======||\n");
	printf("||======5.查看通讯录======||\n");
	printf("||=========0.退出=========||\n");
}

int main()
{
	contact* con;
	InitContact(&con);
	int input = 0;
	do
	{
		menu();
		printf("请选择:>");
		scanf("%d", &input);
		switch (input)
		{
		case Exit:
            DestroyContact(&con);
			printf("退出!\n");
			break;
		case Add:
			AddContact(&con);
			break;
		case Del:
			DelContact(&con);
			break;
		case Find:
			FindContact(con);
			break;
		case Modi:
			ModifyContact(&con);
			break;
		case Show:
			ShowContact(con);
			break;
		default:
			printf("输入错误,请重新输入!\n");
			break;
		}
		system("pause"); fflush(stdin); system("cls");
	} while (input);


	return 0;
}

下面这一行的作用是

1. 暂停让用户看执行结果。

2. 清除输入缓存,防止输入粘连。

3. 清空屏幕,以免屏幕上留下太多信息。

system("pause"); fflush(stdin); system("cls");

5. 运行展示

5.1 增加联系人

5.2 删除联系人

 5.3 查找联系人

5.4 修改联系人

 5.5 查看通讯录

  • 21
    点赞
  • 18
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 13
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 13
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

大筒木老辈子

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值