鏈表實現學生管理系統


makefile

 

main : main.o stu.o llist.o gcc -Wall -o $@ $^ clean : rm -rf main *.o

 

 

 

頭文件

llist.h

#ifndef __LLIST_H #define __LLIST_H

enum a { HEADINSERT, TAILINSERT }; typedef void (llist_print)(const void *data); typedef int (llist_cmp)(const void *data, const void *cp); typedef void LLIST; LLIST *llist_handler(int size); int llist_insert(LLIST *h, const void *data, int mode); int llist_delect(LLIST *h, const void *data, llist_cmp cmp); void *llist_find(LLIST *h, const void *data, llist_cmp cmp); void *llist_display(LLIST *h, llist_print print); void *llist_destroy(LLIST *h); int llist_fetch(LLIST *handler, void *b_data, llist_cmp cmp, void *save); int llist_output(LLIST *h, void *save); #endif

stu.h

#ifndef __STU_H #define __STU_H #include "llist.h"

struct stu { int id; char name[20]; long int tel; }; void insert_data(LLIST *handler); int delect_data(LLIST *handler); int    fetch_data(LLIST *handler); int find_data(LLIST *handler); void display_data(LLIST *handler); void sort_data(LLIST *handler); int save_data(LLIST *handler); int read_data(LLIST *handler); #endif

llist.c

#include <stdio.h> #include <stdlib.h> #include <string.h> #include "llist.h"

struct llist_node { struct llist_node *prev; struct llist_node *next; char data[0]; }; struct head_node { int size; struct llist_node node; }; LLIST *llist_handler(int size) { struct head_node *handler = NULL; handler = malloc(sizeof(LLIST)); if(handler == NULL) return NULL; handler->size = size; handler->node.prev = handler->node.next = &handler->node; return handler; } int llist_insert(LLIST *h, const void *data, int mode) { struct head_node *handler = h; struct llist_node *newnode = NULL; struct llist_node *p = &handler->node; newnode = malloc(sizeof(struct llist_node) + handler->size); if(newnode == NULL) return -1; memcpy(newnode->data, data, handler->size); switch(mode) { case HEADINSERT :    break; case TAILINSERT :    p = p->prev; break; default : free(newnode); break; } newnode->next = p->next; newnode->prev = p->next->prev; newnode->prev->next = newnode; newnode->next->prev = newnode; return 0; } struct llist_node *_find(LLIST *h, const void *data, llist_cmp cmp) { struct head_node *handler = h; struct llist_node *cur = NULL; for(cur = handler->node.next; cur != &handler->node; cur = cur->next) { if(cmp(cur->data, data)) return cur; } return NULL; } void *llist_find(LLIST *h, const void *data, llist_cmp cmp) { struct head_node *handler = h; struct llist_node *find = NULL; find = _find(handler, data, cmp); if(NULL == find) return NULL; return find->data; } int llist_delect(LLIST *h, const void *data, llist_cmp cmp) { struct head_node *handler = h; struct llist_node *find = NULL; find = _find(handler, data, cmp); if(NULL == find) return -1; find->prev->next = find->next; find->next->prev = find->prev; free(find); } void *llist_display(LLIST *h, llist_print print) { struct head_node *handler = h; struct llist_node *cur = handler->node.next; while(cur != &handler->node) { print(cur->data); cur = cur->next; } } void *llist_destroy(LLIST *h) { struct head_node *handler = h; struct llist_node *p = NULL; struct llist_node *cur = NULL; for(p = handler->node.next; p != &handler->node; p = p->next) { cur = p; p->next->prev = p->prev; p->prev->next = p->next; free(p); p = cur; } free(handler); } int llist_fetch(LLIST *h, void *b_data, llist_cmp cmp, void *save) { struct head_node *handler = h; struct llist_node *cur = NULL; struct llist_node *find = NULL; find = _find(handler, b_data, cmp); if(NULL == find) return -1; memcpy(save, find->data, handler->size); find->next->prev = find->prev; find->prev->next = find->next; free(find); } int llist_output(LLIST *h, void *save) { struct head_node *handler = h; struct llist_node *cur = handler->node.next; if(cur == &handler->node) return -1; cur->next->prev = cur->prev; cur->prev->next = cur->next; memcpy(save, cur->data, handler->size); free(cur); }

stu.c

#include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <string.h> #include "stu.h"

static int a, ret, b, bnum, num; static char name[20]; static char bname[20]; static long int tel, lbnum, lnum; void print(const void *data)    //打印函數
{ const struct stu *p = data; printf("%d %s %ld\n", p->id, p->name, p->tel); } int id_cmp(const void *data, const void *cp)    //id對比函數
{ const struct stu *p = data; const int *cur = cp; return !(p->id - *cur); } int tel_cmp(const void *data, const void *cp) { const struct stu *p = data; const long int *cur = cp; return !(p->tel - *cur); } int name_cmp(const void *data, const void *cp)        //名字對比函數
{ const struct stu *p = data; const char *cur = cp; return !(strcmp(cur, p->name)); } void insert_data(LLIST *handler)                //增加數據函數
{ struct stu data; struct stu *find = NULL; system("clear"); printf("請輸入學號:\n"); scanf("%d", &num); find = llist_find(handler, &num, id_cmp); if(find != NULL) { printf("該學號已存在,請核對后從新輸入!\n"); sleep(2); return ; } data.id = num; printf("請輸入學生姓名:\n"); scanf("%s", name); memcpy(data.name, name, 20); printf("請輸入學生電話:\n"); scanf("%ld", &tel); data.tel = tel; ret = llist_insert(handler, &data, HEADINSERT); if(ret < 0) printf("未能成功添加學生信息。\n"); else printf("成功添加學生信息。\n"); sleep(2); } int delect_data(LLIST *handler)                //刪除數據函數
{ LEAP : printf("1.輸入學號刪除\t2.輸入姓名刪除\n"); scanf("%d", &b); if(b == 1) { system("clear"); printf("請輸入要刪除學生的學號:\n"); scanf("%d", &num); ret = llist_delect(handler, &num, id_cmp); if(ret < 0) return -1; else printf("成功刪除學號為%d的學生信息。\n", num); } else if(b == 2) { system("clear"); printf("請輸入要刪除學生的姓名:\n"); scanf("%s", name); ret = llist_delect(handler, name, name_cmp); if(ret < 0) return -1; else printf("成功刪除姓名為%s的學生信息\n", name); } else { system("clear"); printf("輸入錯誤,請重新輸入\n"); goto LEAP; } } int    fetch_data(LLIST *handler)            //修改數據函數,修改數據后不排序
{ struct stu save; LEAP1: printf("請選擇你要修改的信息:\n1.修改學號 2.修改姓名 3.修改電話\n"); scanf("%d", &b); if(b == 1) { system("clear"); printf("請輸入你要修改的學號:\n"); scanf("%d", &bnum); printf("請輸入新的學號:\n"); scanf("%d", &num); ret = llist_fetch(handler, &bnum, id_cmp, &save); if(ret < 0) return -1; else { save.id = num; ret = llist_insert(handler, &save, HEADINSERT); if(ret < 0) return -2; goto PRINT; } } else if(b == 2) { system("clear"); printf("請輸入你要修改的學生姓名:\n"); scanf("%s", bname); printf("請輸入修改后的學生姓名:\n"); scanf("%s", name); ret = llist_fetch(handler, bname, name_cmp, &save); if(ret < 0) return -1; else { memcpy(save.name, name, 20); ret = llist_insert(handler, &save, HEADINSERT); if(ret < 0) return -2; else
            goto PRINT; } } else if(b == 3) { system("clear"); printf("請輸入你要修改的電話:\n"); scanf("%ld", &lbnum); printf("請輸入新的電話:\n"); scanf("%ld", &lnum); ret = llist_fetch(handler, &lbnum, tel_cmp, &save); if(ret < 0) return -1; else { save.tel = lnum; ret = llist_insert(handler, &save, HEADINSERT); if(ret < 0) return -2; goto PRINT; } } else { system("clear"); printf("輸入錯誤,請重新輸入\n"); goto LEAP1; } PRINT: printf("修改成功!該學生的最新信息為:\n"); print(&save); } int find_data(LLIST *handler)        //查找數據函數
{ struct stu *find = NULL; LEAP: printf("請選擇查找方式:\n1.通過學號查找\t2.通過姓名查找\n"); scanf("%d", &a); if(a == 1) { system("clear"); printf("請輸入學號:\n"); scanf("%d", &num); find = llist_find(handler, &num, id_cmp); if(ret < 0) return -1; goto PRINT; } else if(a == 2) { system("clear"); printf("請輸入姓名:\n"); scanf("%s", name); find = llist_find(handler, name, name_cmp); if(ret < 0) return -1; goto PRINT; } else { system("clear"); printf("輸入錯誤, 請重新輸入!\n"); goto LEAP; } PRINT: printf("已找到!\n"); print(find); } void display_data(LLIST *handler)        //打印數據函數
{ system("clear"); llist_display(handler, print); } void sort_data(LLIST *handler)        //排序函數,上限100個
{ struct stu save[100] = {}; struct stu tmp; struct stu s; int i = 0, j = 0, a = 0; for(i = 0; i < 100; i++) { ret = llist_output(handler, &s); if(ret < 0) break; memcpy(&save[i], &s, sizeof(struct stu)); } a = i; for(i = 0; i < 99; i++) { for(j = 0; j < 99 - i; j++) { if(save[j].id < save[j+1].id) { memcpy(&tmp, &save[j], sizeof(struct stu)); memcpy(&save[j], &save[j+1], sizeof(struct stu)); memcpy(&save[j+1], &tmp, sizeof(struct stu)); } } } for(i = 0; i < a; i++) { ret = llist_insert(handler, &save[i], HEADINSERT); if(ret < 0) break; } printf("排序完成!\n"); sleep(2); } int save_data(LLIST *handler)        //打印到文件
{ FILE *fp = NULL; struct stu save; fp = fopen("data_save", "r+"); if(fp == NULL) return -1; while(1) { ret = llist_output(handler, &save); if(ret < 0) break; ret = fprintf(fp, "%d\t\t\t%s\t\t\t%ld\n", save.id, save.name, save.tel); if(ret == EOF) { fclose(fp); perror("fprintf()"); return -1; } } fclose(fp); fp = NULL; printf("向文件寫入成功!\n"); sleep(2); } int read_data(LLIST *handler)        //從文件導入鏈表
{ FILE *fp = NULL; struct stu save; fp = fopen("data_save", "r+"); if(fp == NULL) return -1; while(1) { ret = fscanf(fp, "%d%s%ld", &save.id, save.name, &save.tel); if(ret == EOF) { perror("fprintf()"); break; } // print(&save);
        llist_insert(handler, &save, HEADINSERT); } fclose(fp); fp = NULL; printf("文件內容以存入鏈表!\n"); sleep(2); }

main.c

#include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <string.h> #include "stu.h" #include "llist.h"


int main(void) { struct stu *data, *save; char d = 0; int a = 0, num = 0, ret = 0, b = 0, bnum = 0; int tel; FILE *fd = NULL; LLIST *handler = NULL; handler = llist_handler(sizeof(struct stu)); if(NULL == handler) return -1; /* fd = fopen("data_save", "w+"); if(fd == NULL) { perror("fopen"); return -1; } ret = fprintf(fd, "%s\t\t\t%s\t\t\t%s\n", "學號", "姓名", "電話"); if(ret == EOF) { fclose(fd); return -1; } fclose(fd); p = NULL; */
    while(1) { system("clear"); printf("-----------------------------------------------------------\n"); printf("---------------------學生管理系統--------------------------\n"); printf("-----------------------------------------------------------\n"); printf("1.增加數據\t2.刪除數據\t3.修改數據\t4.查找數據\n5.打印數據\t6.排序數據\t7.保存文件\t8.讀取文件\n9.退出系統\n"); printf("請輸入序號操作\n"); scanf("%d", &a); switch(a) { case 9:    return 0; case 1: insert_data(handler); break; case 2:    ret = delect_data(handler); if(ret < 0) printf("刪除失敗!沒有該學生信息。\n"); sleep(2); break; case 3:    ret = fetch_data(handler); if(ret == -1) printf("修改失敗!未找到該學生的信息。\n"); else if(ret == -2) printf("修改失敗!\n"); sleep(2); break; case 4:    ret = find_data(handler); if(ret < 0) printf("未找到該學生信息。\n"); sleep(2); break; case 5: display_data(handler); printf("按q退出\n"); getchar(); scanf("%c", &d); if(d == 'q' || d == 'Q') break; case 6: sort_data(handler); break; case 7: save_data(handler); break; case 8: read_data(handler); break; default:    printf("輸入有誤!\n"); sleep(3); break; } } return 0; }

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM