点击蓝字 关注我们

不仅仅是图书信息管理系统

基于双链表,采用面向对象编程方法制作的图书管理系统

效果演示

root用户:账号:0,密码:0

普通用户:账号:1001,密码:666666

图书信息

没有完全演示,只是个大概,微信gif只能300帧以内

框架结构

数据层:双链表管理

核心层:用户管理、图书管理

用户管理:

用户分三种:readonly、write、root(可删除数据)

功能:Exit(退出), Add(添加), Show(显示), Change(修改), Delete(删除), Search(查找)

图书管理:

权限分级:暂未实现(可自行实现)

功能:EXIT(退出), ADD(添加), SHOW(显示), CHANGE(修改), DELETE(删除), SEARCH(查找)

ps:用这个双链表框架可以解决99.9%的各种信息管理系统(增删改查)问题,那%0.1就是给自己留的后路,毕竟没有什么问题可以100%解决

以后再跟我提xxx管理系统我就给你扔过去这对代码,自己去实现

核心部分:双链表的实现

双链表
typedef struct deroy_node{void* data;struct deroy_node* prev;struct deroy_node* next;}deroy_node_t;typedef deroy_node_t* deroy_node_pt;

typedef struct deroy_list{int  limit_size;    deroy_node_pt head;    deroy_node_pt tail;}deroy_list_t;typedef deroy_list_t* deroy_list_pt;

为什么链表里面的data是void*呢,谭浩强的C语言不是这样教的啊

void类型是空类型,可以转成任意一种类型,你不知道你插入的数据的结构体是什么,或者说你要插入多种数据的结构体,确定的结构体已经不能够满足需求了,需要定义void*类型来指向你要添加进链表的结构体数据

我们需要实现一些函数来管理链表,注意o,前方高能,小白勿看

功能函数

/*初始化链表*/deroy_list_pt deroy_list_create(void);/*插入节点*/int deroy_list_insert_before(deroy_list_t** list_head, int num, void* new_node_data);/*删除节点*/int deroy_list_delete(deroy_list_t** list_head, int num);/*修改节点*/int deroy_list_modify(deroy_list_t** list_head, int num, void* new_node_data);/*遍历节点*/void deroy_list_cuid(deroy_list_t* list_head, void (*do_function)(void*));/*查询数据 返回 数据的位置*/int deroy_list_search(deroy_list_t** list_head, void* find_data, int(*compare)(void*, void*));/*查询数据 返回 数据的指针*/void* deroy_list_find(deroy_list_t** list_head, void* find_data, int(*compare)(void*, void*))

为什么我要先把功能函数的原型给列举出来,因为你仔细看参数,双链表功能实现多次用到回调函数

什么是回调函数呢?

回调函数就是一个通过函数指针调用的函数。❞

怎么说呢,如果你把函数的指针(地址)作为参数传递给另一个函数,当这个指针被用来调用其所指向的函数时,我们就说这是回调函数。

回调函数能够干什么?

你学过C++知道多肽吧,就是一个方法实现多个功能,回调函数就是C里面实现多肽的方式

举个栗子:

功能函数里面有个遍历所有节点的功能函数

/*遍历节点*/void deroy_list_cuid(deroy_list_t* list_head, void (*do_function)(void*)){int i = 0;if (list_head == NULL || list_head->limit_size < 0)    {        errno = EINVAL;exit(errno);    }for (i = 0; i < list_head->limit_size; i++)    {        (*do_function)(__deroy_list_visit(&list_head, i));    }}

前面那个判断没啥可看的,直接看 (*do_function)(__deroy_list_visit(&list_head, i));

__deroy_list_visit是个内联函数,它的功能就是返回list_head里面的第i个节点数据(void *data)

然后将数据给传入的do_function,让dofunction去处理data数据,核心层用户管理区实现dofunction

/*回调函数 打印所以学生信息*/static void proxy_find_stu(deroy_data_pt pdata){/*遍历学生信息*/if (pdata->type == STU)    {printf(" %d\t%d\t%s\t%d\t%d\n", pdata->type, pdata->id, pdata->name, pdata->sex, pdata->rank);    }}

/*回调函数 root用户打印所有信息*/static void proxy_find_all(deroy_data_pt pdata){/*遍历所有信息*/printf(" %d\t%d\t%s\t%d\t%d\t%d:\t%s\n", pdata->type, pdata->id, pdata->name, pdata->sex, pdata->rank, pdata->acount,pdata->password);}

通过对dofunction的实现,我们一个deroy_list_cuid函数可以遍历所有data的id段,还是不管什么数据都打印,这样就实现了root用户查看的权限更大

如果觉得这个直接两个函数实现不是更好吗,如果你想到这里,证明你还在思考,对,两个函数实现更方便,但是,那是核心层(自己写回调函数)去重新解释这个功能,达到了分层的概念

或许这里的回调函数应用的不明显,这里还有个明显的

/*查询数据 返回 数据的位置*/int deroy_list_search(deroy_list_t** list_head, void* find_data, int(*compare)(void*, void*)){int counter = 1;    deroy_node_pt current = NULL;if (list_head == NULL || *list_head == NULL)    {        errno = EINVAL;exit(errno);    }if ((*list_head)->limit_size == 0)    {return -1;  //无数据可查询    }    current = (*list_head)->head;/*通过传入的comper函数进行比较*/while (compare(current->data, find_data) == 0 && current->next != NULL)    {        current = current->next;        counter++;    }if (current->next == NULL && compare(current->data, find_data) == 0)return 0;return counter;}

这里的的回调函数要求判断两个数据,返回真假

/*回调函数 比较db_data_pt数据段的id是否相同*/static int proxy_compare_id(deroy_data_pt pdata, deroy_data_pt other){if (pdata->id == other->id)return 1;return 0;}

通过核心层的用户管理去实现按id查找,还是其他查找方式,这里你总不能两个函数解决吧,必须要分层

不能扯太远,咱说的是链表,继续..

双链表的实现,我之前发过一篇循环双链表,有图解,还算详细

循环双链表

这个双链表还算可以,没有内存泄漏(如果有请告诉我,反正我也不会去改),各种判断安全系数高,功能完善,能处理各种增删改查功能的系统设计

核心层:用户管理

啊~当时想着用双链表实现学生信息管理系统来着,码着码着就想把图书信息管理系统也码下来,比较学生信息管理系统已经烂大街了,我上个学生信息管理系统在知乎都有2000赞了

#define STU 0#define TEACHER 1

typedef enum Menu{    Exit, Add, Show, Change, Delete, Search}MENU;

typedef enum Sex{    MAN, WOMAN}SEX;

/*权限*/enum RANK{    READ_ONLY   /*只读*/    , WRITE     /*读写*/    , ROOT      /*root可删除*/};

/*学号、专业、姓名、年龄、性别属性。*/

typedef struct deroy_data{char   type;    /*类型*/char   rank;    /*级别*/int    id;      /*编号*/char   name[10];    /*姓名*/char   sex;         /*性别*/int    acount;      /*账号*/char   password[20];    /*密码*/void*  data;        /*其他*/int(*Init)(struct deroy_data* pdata);}deroy_data_t;typedef deroy_data_t* deroy_data_pt;

没什么特殊的,甚至用户信息少的可怜,有点用处的就是权限了,然后看到deroy_data里面的void* data段了吗,没错,我就是想告诉你们,这个是扩展功能,可扩展用户的其他信息,这个我就不实现了,比较代码多了,你们看着挺烦的

然后这个结构体里面的函数指针,就相当于C++里面的方法,可以指向一个功能函数

然后就和之前的学生信息管理系统差不多了~

/*学生信息管理系统*/int system_proxy_stu(deroy_list_pt ptlist,int user_rank){    rank = user_rank;while (1)    {switch (menu_proxy_stu())  //菜单选择        {case Exit:       //退出程序            system("cls");printf("退出程序\n");            Quit();return 1;break;case Show:       //显示所有学生信息            system("cls");if (rank == READ_ONLY)            {printf(" 类型\t学号\t姓名\t性别\t权限\n\n");                deroy_list_cuid(ptlist, proxy_find_stu);            }else if(rank == ROOT)            {printf(" 类型\t学号\t姓名\t性别\t权限\t账号:\t密码\n\n");                deroy_list_cuid(ptlist, proxy_find_all);            }            Quit();break;case Add:     //添加学生信息            init_proxy_stu(ptlist);            Quit();break;case Change:    //修改学生信息            proxy_stu_modify(ptlist);            Quit();break;case Delete:  //删除学生信息            proxy_stu_delete(ptlist);            Quit();break;case Search:  //查询学生信息            proxy_stu_find(ptlist);            Quit();break;        }        system("cls");    }}

把所有功能函数都实现了,并且功能函数都有权限设置,普通用户只能查看普通用户的信息

核心层:图书管理

这个图书管理实现的比用户管理还简单,我都没去设置权限问题,可自行设计

typedef enum BookMenu{    EXIT, ADD, SHOW, CHANGE, DELETE, SEARCH}BOOKMENU;

/*图书编号、书名、图书分类、数量、出版日期、登记日期*/typedef struct deroy_book{int  iID;            /*序号*/char cId[4];         /*编号*/char cName[20];      /*书名*/char cSubject[20];   /*图书分类*/int  iNums;           /*数量*/char cPublish_data[20];/*出版日期*/char cData[20];        /*登记日期*/int(*Init)(struct deroy_book* pdata);   /*初始化函数*/}deroy_book_t;typedef deroy_book_t* deroy_book_pt;

简简单单的把基本的图书信息给列举出来,只需要实现功能函数即可

/*初始化图书数据*/static void init_book_proxy_node(deroy_book_pt self)/*注册图书*/static void register_book_proxy_method(deroy_list_pt ptlist, void* pdata)/*初始化图书信息*/static void init_proxy_book(deroy_list_pt ptlist)/*菜单选择*/static int menu_proxy_book()/*修改图书信息*/static void proxy_book_modify(deroy_list_pt ptlist)/*删除图书信息*/static void proxy_book_delete(deroy_list_pt ptlist)/*查找图书信息*/static void proxy_book_find(deroy_list_pt ptlist)/*图书信息管理系统*/int system_proxy_book(deroy_list_pt ptlist)

这些个功能函数都挺简单的,都是围绕着之前设计的链表来实现的,详情可以看原码

这其实就是我将用户管理的代码复制过来,改void *data所指向的结构体deroy_book,几乎是一模一样的,所以说这是个模板,是个框架,框架定死了,你围绕着这个框架去实现功能就行

这里提个有趣的:就是图书注册日期,这里不用管理员去实现,直接sprintf(self->cData, "%s", __DATE__);__DATE__是一个宏,打印的是当前日期,打印的是年月日例如Jul 11 2020,这个宏我在C语言预处理那里提过,可惜看的人不多,

预处理

用户登录

首先主函数里面把两个核心层给创建咯,

   deroy_list_pt pStu_Head = deroy_list_create(); //创建用户    deroy_list_pt pBook_Head = deroy_list_create();    //创建书籍

在创建用户的时候会创建两个用户对象,一个root、一个普通read_only,用于初始登录

登录就是去调用函数,接收函数的返回值

   int user_rank = load(pStu_Head);if (user_rank < 0)  {printf("登录失败");return 0;   }

这个返回值是用户的权限,用来层级之间交互

int load(deroy_list_pt phead){char account[20],password[20];   //账号密码printf("input acount:");scanf("%s", account);printf("password:");scanf("%s", password);deroy_data_t temp; temp.id = atoi(account); deroy_data_pt find_data = deroy_list_find(&phead, &temp, proxy_compare_load);if (find_data >= 0)   {if (strcmp(password, find_data->password) == 0)       {return find_data->rank;     } }return -1;}

之而立直接调用链表提供的方法deroy_list_find,自己实现回调函数

int proxy_compare_load(deroy_data_pt pdata, deroy_data_pt other){if (pdata->id == other->id)return 1;return 0;}

为什么是找id而不是用户名呢,这里我懒了一下,直接将id赋值给account,整数方便,图个开心

「公众号【编程学习基地】后台发送关键字「图书信息管理系统」获取源代码」

关键字【图书管理系统】

End


作者:梦凡梦想在,终不凡~你们的在看就是对我最大的肯定,点个在看好吗~


编程学习基地常回基地看看

实现图书增删的代码_不仅仅是图书信息管理系统相关推荐

  1. python综合管理系统代码_《python学生信息管理系统》[52KB]PDF代码版下载-码农之家...

    <python学生信息管理系统>是一本python相关的电子书资源,介绍了关于python.学生管理系统方面的内容,格式为PDF,资源大小52 KB,由26622451 提供,目前在&qu ...

  2. 用户管理界面开源代码_某教师培训信息管理系统渗透思路分享

    上周公司开完会,感觉到阵阵压力.我的领导偷偷和我们在群里聊了很多.后来他心血来潮突然丢了个教师系统给我们练手于是就有了后续的事情 . 整个界面比较简单没有什么可以突破的地方.看到忘记密码点进去发现并没 ...

  3. C++课程设计实训_基于多态书籍信息管理系统的设计与实现、附源码、有过程截图

    C++课程设计实训_基于多态书籍信息管理系统的设计与实现.附源码,有过程截图 书籍信息管理系统的设计与实现(基于多态) 学生姓名: 学 号: 指导老师: 所 在 系: 专 业: 班 级: C++课程设 ...

  4. java查询学生信息_分别显示女生_女生学生基本信息的代码_java课程设计学生信息管理系统_毕业论文.doc...

    java课程设计学生信息管理系统_毕业论文 学 号: 课 程 设 计 题 目学生信息管理系统学 院计算机科学与信息工程学院专 业金融信息化服务外包班 级学生姓名指导教师 2015年12月28日 课程设 ...

  5. java图书列表打印系统_定义一个图书列表打印系统,

    /* * 图书类Book */ public class Book { private String id; //图书编号 private String bookname; //图书名称 privat ...

  6. python学生成绩管理系统实验报告_【python 学生信息管理系统】

    1. 简述 本文讲述的是用 python 语言写一个简单的学生信息管理系统,系统包含学生信息的增删查改功.同时使用了 mysql5.7.14 来存储数据. 2.准备工作 首先,先搭建好自己的 MySQ ...

  7. html增加状态信息管理代码,JavaScript+HTML实现学生信息管理系统

    一.前言 用数组来存储所有学生对象的信息,实现了双向更新,初始时(数组内的对象信息"填充界面"),后面的界面操作可以更新数组内对象的信息(数量和本身数据域信息). 优点:JQuer ...

  8. c语言添加学生信息代码,《C语言-学生信息管理系统(代码)》.doc

    X X 师 范 大 学 实 验 报 告 课 程 C语言课程设计 任课老师 学 号 姓 名 院 系 _______年______月至_______年_______月 注意事项 使用C语言,代码已在vs中 ...

  9. java 公交管理系统 代码_基于jsp的公交管理系统-JavaEE实现公交管理系统 - java项目源码...

    基于jsp+servlet+pojo+mysql实现一个javaee/javaweb的公交管理系统, 该项目可用各类java课程设计大作业中, 公交管理系统的系统架构分为前后台两部分, 最终实现在线上 ...

最新文章

  1. 记录Datagrid使用的一些事项
  2. shell脚本if参数太多_Shell脚本用for循环遍历参数的方法技巧
  3. Spark RDD并行度与分区设置
  4. 8.Eclipse中创建Maven Web项目
  5. python atm作业详解_python day4 作业 ATM
  6. IDEA 实用功能Auto Import:自动优化导包(自动删除、导入包)
  7. python环境配置opencv_Python 3.5.1和Opencv 3.1的环境配置
  8. python解释器把python代码一次性翻译成目标代码_Python语言程序设计----【第1周 Python基本语法元素】之1.1 程序设计基本方法...
  9. 支持蓝牙的模拟器_横竖都能玩的小鸡G6,蓝牙连接尽情享受手游乐趣
  10. 富文本点击事件-TTTAttributedLabel和YYtext的不同用法
  11. 数据分析案例-气象数据分析
  12. android微信7,微信7.0安卓版之初体验
  13. android相机预览拍照功能实现
  14. 如何连接苹果电脑打印服务器
  15. python中readlines是什么意思_python中read、readline、readlines之间的区别
  16. SpringSecurity 学习笔记分享 记录历程开篇
  17. 从零开始学习TradingView Pine脚本编程
  18. Expert Metalink – Support Tips Tools Resources
  19. CC2530定时器T1产生PWM
  20. 出现Joi.validate is a not function解决办法

热门文章

  1. Linux 中的文件压缩与解压
  2. 教你如何在 elasticsearch 中重建索引
  3. Java语言中的-----访问修饰符
  4. 设计模式 之 《组合模式》
  5. Halcon:手眼标定——眼在手外与眼在手上
  6. 中国智能高清视频监控未来发展趋势
  7. get_metrology_object_measures获取测量区域和计量模型的计量对象的边缘位置结果
  8. 【深度学习】mask_rcnn训练自己的数据集以及模型使用(实践结合GitHub项目)
  9. matlab常用函数——数学函数
  10. 最优化课堂笔记05——一维最优化方法(含重点:黄金分割法)