知者何南 发表于 2025-1-22 14:53:03

【数据布局】双向循环链表实现浅易图书管理系统的增删改查

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

// 书籍结构体
struct book {
    char name;      // 书名
    char authorname; // 作者名
    float price;      // 价格
    int num;            // 总数量
    int borrowed;       // 已借出数量
};

// 双向循环链表节点
struct node {
    struct book data;
    struct node *prev;
    struct node *next;
};

// 全局变量:链表头指针
struct node *head = NULL;

// 函数声明
void add_book();
void delete_book();
void modify_book();
void search_book();
void borrow_book();
void return_book();
void display_all();
void free_list();
struct node* find_book(char *name);

int main() {
    int choice;
    while (1) {
      printf("\n图书管理系统\n");
      printf("1. 添加书籍\n");
      printf("2. 删除书籍\n");
      printf("3. 修改书籍信息\n");
      printf("4. 查询书籍信息\n");
      printf("5. 借书\n");
      printf("6. 还书\n");
      printf("7. 显示所有书籍\n");
      printf("0. 退出\n");
      printf("请选择操作: ");
      scanf("%d", &choice);

      switch (choice) {
            case 1: add_book(); break;
            case 2: delete_book(); break;
            case 3: modify_book(); break;
            case 4: search_book(); break;
            case 5: borrow_book(); break;
            case 6: return_book(); break;
            case 7: display_all(); break;
            case 0: free_list(); return 0;
            default: printf("无效选择!\n");
      }
    }
    return 0;
}

// 添加书籍
void add_book() {
    struct node *new_node = (struct node*)malloc(sizeof(struct node));
    if (!new_node) {
      printf("内存分配失败!\n");
      return;
    }

    printf("请输入书名: ");
    scanf("%s", new_node->data.name);
    printf("请输入作者名: ");
    scanf("%s", new_node->data.authorname);
    printf("请输入价格: ");
    scanf("%f", &new_node->data.price);
    printf("请输入总数量: ");
    scanf("%d", &new_node->data.num);
    new_node->data.borrowed = 0;

    if (!head) {
      head = new_node;
      head->next = head;
      head->prev = head;
    } else {
      new_node->next = head;
      new_node->prev = head->prev;
      head->prev->next = new_node;
      head->prev = new_node;
    }
    printf("书籍添加成功!\n");
}

// 删除书籍
void delete_book() {
    if (!head) {
      printf("没有书籍可删除!\n");
      return;
    }

    char name;
    printf("请输入要删除的书名: ");
    scanf("%s", name);

    struct node *current = head;
    do {
      if (strcmp(current->data.name, name) == 0) {
            if (current->data.borrowed > 0) {
                printf("该书还有借出未还,不能删除!\n");
                return;
            }

            if (current == head) {
                if (head->next == head) {
                  head = NULL;
                } else {
                  head = head->next;
                }
            }

            current->prev->next = current->next;
            current->next->prev = current->prev;
            free(current);
            printf("书籍删除成功!\n");
            return;
      }
      current = current->next;
    } while (current != head);

    printf("未找到该书!\n");
}

// 修改书籍信息
void modify_book() {
    if (!head) {
      printf("没有书籍可修改!\n");
      return;
    }

    char name;
    printf("请输入要修改的书名: ");
    scanf("%s", name);

    struct node *book = find_book(name);
    if (!book) {
      printf("未找到该书!\n");
      return;
    }

    printf("当前信息:\n");
    printf("书名: %s\n", book->data.name);
    printf("作者: %s\n", book->data.authorname);
    printf("价格: %.2f\n", book->data.price);
    printf("总数量: %d\n", book->data.num);
    printf("已借出: %d\n", book->data.borrowed);

    printf("\n请输入新的作者名: ");
    scanf("%s", book->data.authorname);
    printf("请输入新的价格: ");
    scanf("%f", &book->data.price);
    printf("请输入新的总数量: ");
    scanf("%d", &book->data.num);

    printf("书籍信息修改成功!\n");
}

// 查询书籍信息
void search_book() {
    if (!head) {
      printf("没有书籍可查询!\n");
      return;
    }

    char name;
    printf("请输入要查询的书名: ");
    scanf("%s", name);

    struct node *book = find_book(name);
    if (!book) {
      printf("未找到该书!\n");
      return;
    }

    printf("\n书籍信息:\n");
    printf("书名: %s\n", book->data.name);
    printf("作者: %s\n", book->data.authorname);
    printf("价格: %.2f\n", book->data.price);
    printf("总数量: %d\n", book->data.num);
    printf("可借数量: %d\n", book->data.num - book->data.borrowed);
}

// 借书
void borrow_book() {
    if (!head) {
      printf("没有书籍可借!\n");
      return;
    }

    char name;
    printf("请输入要借的书名: ");
    scanf("%s", name);

    struct node *book = find_book(name);
    if (!book) {
      printf("未找到该书!\n");
      return;
    }

    int available = book->data.num - book->data.borrowed;
    printf("当前可借数量: %d\n", available);
   
    if (available <= 0) {
      printf("该书已全部借出!\n");
      return;
    }

    int quantity;
    printf("请输入要借的数量: ");
    scanf("%d", &quantity);
   
    if (quantity <= 0) {
      printf("借书数量必须大于0!\n");
      return;
    }
   
    if (quantity > available) {
      printf("借书数量超过可借数量!\n");
      return;
    }

    book->data.borrowed += quantity;
    printf("借书成功! 当前已借出: %d\n", book->data.borrowed);
}

// 还书
void return_book() {
    if (!head) {
      printf("没有书籍可还!\n");
      return;
    }

    char name;
    printf("请输入要还的书名: ");
    scanf("%s", name);

    struct node *book = find_book(name);
    if (!book) {
      printf("未找到该书!\n");
      return;
    }

    if (book->data.borrowed <= 0) {
      printf("该书没有借出记录!\n");
      return;
    }

    printf("当前已借出数量: %d\n", book->data.borrowed);
   
    int quantity;
    printf("请输入要还的数量: ");
    scanf("%d", &quantity);
   
    if (quantity <= 0) {
      printf("还书数量必须大于0!\n");
      return;
    }
   
    if (quantity > book->data.borrowed) {
      printf("还书数量超过已借出数量!\n");
      return;
    }

    book->data.borrowed -= quantity;
    printf("还书成功! 当前已借出: %d\n", book->data.borrowed);
}

// 显示所有书籍
void display_all() {
    if (!head) {
      printf("没有书籍可显示!\n");
      return;
    }

    struct node *current = head;
    printf("\n所有书籍信息:\n");
    do {
      printf("\n书名: %s\n", current->data.name);
      printf("作者: %s\n", current->data.authorname);
      printf("价格: %.2f\n", current->data.price);
      printf("总数量: %d\n", current->data.num);
      printf("可借数量: %d\n", current->data.num - current->data.borrowed);
      current = current->next;
    } while (current != head);
}

// 释放链表内存
void free_list() {
    if (!head) return;

    struct node *current = head;
    struct node *temp;
    do {
      temp = current;
      current = current->next;
      free(temp);
    } while (current != head);
}

// 查找书籍
struct node* find_book(char *name) {
    if (!head) return NULL;

    struct node *current = head;
    do {
      if (strcmp(current->data.name, name) == 0) {
            return current;
      }
      current = current->next;
    } while (current != head);

    return NULL;
}


免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
页: [1]
查看完整版本: 【数据布局】双向循环链表实现浅易图书管理系统的增删改查