用B-树实现虚拟图书管理系统
来源:互联网 发布:湖南省地质测绘院 知乎 编辑:程序博客网 时间:2024/06/09 21:48
学校数据结构的课程实验之一。
用到的数据结构:B-树
基本功能:对虚拟书库的图书进行查看、增加、删除、修改。
主函数:
#include <iostream>#include "Library.h"using namespace std;int main(){ Library myLib=Library("books.txt"); char choice='y'; while(choice=='y') { cout << "请选择操作"<<endl; cout << "--------------------------------" << endl; cout << "1----新书入库" << endl; cout << "2----查看库存" << endl; cout << "3----借阅" << endl; cout << "4----归还" << endl; cout << "5----删除旧书" << endl; cout << "6----修改图书信息" << endl; cout << "--------------------------------" << endl; int option; cin >> option; switch (option) { case 1: myLib.add(); break; case 2: myLib.display(); break; case 3: myLib.lend(); break; case 4: myLib.back(); break; case 5: myLib.remove(); break; case 6: myLib.change(); break; } cout << "继续吗?[y/n]"; cin >> choice; } cout << "是否保存修改?[y/n]"; cin >> choice; if (choice == 'y') myLib.save("books.txt");//需要保存时保存文件 return 0;}
图书馆类:
#include <string>#include "B_tree.h"using namespace std;struct Book{ int number; string name; string introduction; unsigned left; Book(){} Book(int num) :number(num), name(""), introduction(""), left(0){}//只有编号的初始化 Book(int num, string nam,string intro, unsigned lef)//完整初始化 :number(num),name(nam),introduction(intro),left(lef){} void print()//显示信息 { cout << "-------------------------------" << endl; cout << "这本书的信息如下:" << endl; cout << "编号: " << number << endl; cout << "书名: " << name << endl; cout << "简介: " << introduction << endl; cout << "剩余数量: " << left << endl; cout << "-------------------------------" << endl; } bool operator==(const Book &b) const//重载关系运算符 { if(this->number == b.number) return true;//编号等即命中 else return false; } bool operator<(const Book &b) const { if (this->number < b.number) return true; else return false; } bool operator>(const Book &b) const { if (this->number > b.number) return true; else return false; }};ofstream outFile;//输出流class Library{private: B_tree<Book,3> books; unsigned total; static void readBook(Book &aBook)//写一本书的内容(一定要是静态的) { outFile<<aBook.number<<endl; outFile<<aBook.name<<endl; outFile<<aBook.introduction<<endl; outFile << aBook.left << endl; } void readFile(const char filename[20])//读文件 { total = 0; ifstream inFile; inFile.open(filename); char trying; while(inFile.is_open() && !inFile.eof()) { //先试探是否为结束符 inFile >> trying; if (trying == '#') break; else { inFile.putback(trying); int number; inFile>>number; string name; inFile>>name; string introduction; inFile>>introduction; unsigned left; inFile>>left; Book aBook=Book(number,name,introduction,left); aBook.print();//显示这本书的信息 books.insert(aBook); total+=left; } } cout << "库存共有图书" << total << "本"<<endl; inFile.close(); } void writeFile(const char filename[20])//写文件 { outFile.open(filename); books.traverse(readBook); outFile << '#';//此处必须有一个结束标识符 outFile.close(); } Book search(int num)//以编号为依据进行查找 { Book se_book(num); books.search_tree(se_book); return se_book; } static void print(Book &aBook)//显示信息(必须是静态的) { cout << "-------------------------------" << endl; cout << "这本书的信息如下:" << endl; cout << "编号: " << aBook.number << endl; cout << "书名: " << aBook.name << endl; cout << "简介: " << aBook.introduction << endl; cout << "剩余数量: " << aBook.left << endl; cout << "-------------------------------" << endl; }public: Library(const char filename[20]) { cout << "这是现在的库存信息:" << endl; readFile(filename); } void add()//增加图书 { cout << "请输入图书信息(编号 书名 简介 数量)" << endl; int num; string name; string introduction; unsigned left; cin >> num >> name >> introduction >> left; Book new_book = Book(num, name, introduction, left); books.insert(new_book); cout << "这本书已入库,信息如下:" << endl; new_book.print(); total += left; } void display()//查看库存 { cout << "这是现在的库存信息:" << endl; books.traverse(print); cout << "库存共有图书" << total << "本" << endl; } void remove()//删除 { cout << "请输入要删除的图书编号:"; int num; cin >> num; Book &old_book =search(num);//通过编号找到这本书的记录 cout << "您即将删除这本书的所有信息:" << endl; old_book.print(); cout << "确定要删除吗?[y/n]"; char choice; cin >> choice; if (choice == 'y') { books.remove(old_book);//删除这本书的记录 cout << "编号为" << num << "的书已成功从库中删除" << endl; total--; } } void lend()//借出 { cout << "请输入要借出的图书编号:"; int num; cin >> num; Book &old_book = search(num);//通过编号找到这本书的记录 old_book.left--; cout << "编号为" << num << "的图书已借出1本,下面是这本书的现存信息:" << endl; old_book.print(); total--; } void change()//修改(先删除再添加) { cout << "请输入要修改的图书编号:"; int num; cin >> num; Book &old_book = search(num); cout << "这是这本书的当前信息:" << endl; old_book.print();//显示这本书之前的信息 books.remove(old_book); cout << "请输入修改后的图书信息(编号 书名 简介 数量)" << endl; string name; string introduction; unsigned left; cin >> num >> name >> introduction >> left; Book new_book = Book(num, name, introduction, left); books.insert(new_book); cout << "这本书的信息已修改为:" << endl; new_book.print(); } void back()//归还 { cout << "请输入要归还的图书编号:"; int num; cin >> num; Book &old_book = search(num);//通过编号找到这本书的记录 old_book.left++; cout << "编号为" << num << "的图书已归还,下面是这本书的现存信息:" << endl; old_book.print(); total++; } void save(const char filename[20]) { writeFile(filename); }};这里写代码片
B-树的实现参考了经典教材”Data Structures and Program Design in C++” Robert L. Kruse, Alexander J. Ryba 高等教育出版社-影印版,代码如下:
#include <iostream>using namespace std;enum Error_code{ success, not_present, overflow, duplicate_error};template <class Record, int order>//阶数(分支数)struct B_node{ int count;//成员数 Record data[order-1]; B_node<Record,order> *branch[order]; B_node(){count=0;}};template <class Record, int order>class B_tree{public: B_tree(){root=NULL;} Error_code search_tree(Record &target) { return recursive_search_tree(root,target); } Error_code insert(const Record &new_entry) { Record median; B_node<Record,order> *right_branch, *new_root; Error_code result=push_down(root,new_entry,median,right_branch); if(result==overflow) { new_root=new B_node<Record,order>; new_root->count=1; new_root->data[0]=median; new_root->branch[0]=root; new_root->branch[1]=right_branch; root=new_root; result=success; } return result; } Error_code remove(const Record &target) { Error_code result; result=recursive_remove(root, target); if(root != NULL && root->count==0) { B_node<Record,order> *old_root=root; root=root->branch[0]; delete old_root; } return result; } void traverse(void (*visit)(Record &)) { recursie_traverse(root,visit); }private: B_node<Record, order> *root; void recursie_traverse(B_node<Record,order> *current, void (*visit)(Record &)) { if(current!=NULL) { for(int i=0; i<current->count; i++) (*visit)(current->data[i]); for(int i=0; i<current->count+1; i++) recursie_traverse(current->branch[i], visit); } } Error_code search_node(B_node<Record,order> *current, const Record &target, int &position) const { position=0; while(position < current->count && (target > current->data[position])) position++; if(position < current->count && target == current->data[position]) return success; else return not_present; } Error_code recursive_search_tree(B_node<Record,order> *current, Record &target) { Error_code result=not_present; int position; if(current != NULL) { result=search_node(current,target,position); if(result==not_present) result=recursive_search_tree(current->branch[position],target); else target=current->data[position]; } return result; } void split_node(B_node<Record,order> *current, const Record &extra_entry, B_node<Record,order> *extra_branch, int position, B_node<Record,order>*&right_half, Record &median) { right_half=new B_node<Record,order>; int mid=order/2; if(position <= mid) { for(int i=mid; i<order-1; i++) { right_half->data[i-mid]=current->data[i]; right_half->branch[i+1-mid]=current->branch[i+1]; } current->count=mid; right_half->count=order-1-mid; push_in(current,extra_entry,extra_branch,position); } else { mid++; for(int i=mid; i<order-1; i++) { right_half->data[i-mid]=current->data[i]; right_half->branch[i+1-mid]=current->branch[i+1]; } current->count=mid; right_half->count=order-1-mid; push_in(right_half,extra_entry,extra_branch,position-mid); } median=current->data[current->count-1]; right_half->branch[0]=current->branch[current->count]; current->count--; } void push_in(B_node<Record,order> *current, const Record &entry, B_node<Record,order> *right_branch, int position) { for(int i=current->count; i>position; i--) { current->data[i]=current->data[i-1]; current->branch[i+1]=current->branch[i]; } current->data[position]=entry; current->branch[position+1]=right_branch; current->count++; } Error_code push_down(B_node<Record,order> *current, const Record &new_entry, Record &median, B_node<Record,order>*&right_branch) { Error_code result; int position; if(current==NULL) { median=new_entry; right_branch=NULL; result=overflow; } else { if(search_node(current,new_entry,position)==success) result=duplicate_error; else { Record extra_entry; B_node<Record,order> *extra_branch; result=push_down(current->branch[position],new_entry, extra_entry,extra_branch); if(result==overflow) { if(current->count < order-1) { result=success; push_in(current,extra_entry,extra_branch,position); } else split_node(current,extra_entry,extra_branch,position, right_branch,median); } } } return result; } void restore(B_node<Record,order> *current, int position) { if(position==current->count) if(current->branch[position-1]->count > (order-1)/2) move_right(current,position-1); else combine(current,position); else if(position==0) if(current->branch[1]->count > (order-1)/2) move_left(current,1); else combine(current,1); else if(current->branch[position-1]->count > (order-1)/2) move_right(current,position-1); else if(current->branch[position+1]->count > (order-1)/2) move_left(current,position+1); else combine(current,position); } void move_left(B_node<Record,order> *current, int position) { B_node<Record,order> *left_branch=current->branch[position-1], *right_branch=current->branch[position]; left_branch->data[left_branch->count]=current->data[position-1]; left_branch->branch[++left_branch->count]=right_branch->branch[0]; current->data[position-1]=right_branch->data[0]; right_branch->count--; for(int i=0; i<right_branch->count; i++) { right_branch->data[i]=right_branch->data[i+1]; right_branch->branch[i]=right_branch->branch[i+1]; } right_branch->branch[right_branch->count]= right_branch->branch[right_branch->count+1]; } void move_right(B_node<Record,order> *current, int position) { B_node<Record,order> *right_branch=current->branch[position+1], *left_branch=current->branch[position]; right_branch->branch[right_branch->count+1]= right_branch->branch[right_branch->count]; for(int i=right_branch->count; i>0; i--) { right_branch->data[i]=right_branch->data[i-1]; right_branch->branch[i]=right_branch->branch[i-1]; } right_branch->count++; right_branch->data[0]=current->data[position]; right_branch->branch[0]=left_branch->branch[left_branch->count--]; current->data[position]=left_branch->data[left_branch->count]; } void combine(B_node<Record,order> *current, int position) { int i; B_node<Record,order> *left_branch=current->branch[position-1], *right_branch=current->branch[position]; left_branch->data[left_branch->count]=current->data[position-1]; left_branch->branch[++left_branch->count]=right_branch->branch[0]; for(i=0; i<right_branch->count; i++) { left_branch->data[left_branch->count]=right_branch->data[i]; left_branch->branch[++left_branch->count]=right_branch->branch[i+1]; } current->count--; for(i=position-1; i<current->count; i++) { current->data[i]=current->data[i+1]; current->branch[i+1]=current->branch[i+2]; } delete right_branch; } void copy_in_predecessor(B_node<Record,order> *current, int position) { B_node<Record,order> *leaf=current->branch[position]; while(leaf->branch[leaf->count] != NULL) leaf=leaf->branch[leaf->count]; current->data[position]=leaf->data[leaf->count-1]; } void remove_data(B_node<Record,order> *current, int position) { for(int i=position; i<current->count-1; i++) current->data[i]=current->data[i+1]; current->count--; } Error_code recursive_remove(B_node<Record,order> *current, const Record &target) { Error_code result; int position; if(current==NULL) result=not_present; else { if(search_node(current,target,position)==success) { result=success; if(current->branch[position]!=NULL) { copy_in_predecessor(current,position); recursive_remove(current->branch[position],current->data[position]); } else remove_data(current,position); } else result=recursive_remove(current->branch[position],target); if(current->branch[position]!=NULL) if(current->branch[position]->count < (order-1)/2) restore(current,position); } return result; }};
0 0
- 用B-树实现虚拟图书管理系统
- 数据结构课设--用B树实现图书管理系统
- 实现图书管理系统
- 图书管理系统实现
- 用OC实现图书管理系统
- 图书管理系统之图书信息管理实现
- 基于B-树的图书管理系统课程设计
- STL实现图书管理系统
- 用Servlet实现简单的图书管理系统
- 图书管理系统读写功能实现
- 图书管理系统具体实现方法
- shell实现的一个图书管理系统
- 简单的图书管理系统php实现
- Java实现简单的图书管理系统
- 图书管理系统登录菜单的实现
- 使用OC实现图书管理系统
- C++实现的小型图书管理系统
- 图书管理系统(文件实现)
- openwrt框架分析
- nmon以及nmon analyser 简易教程
- 串口线与并口线的区别
- IOS Application生命周期
- !=小知识点
- 用B-树实现虚拟图书管理系统
- D D - Om Nom and Necklace
- PostgreSQL入门学习之数据库连接相关基础知识
- 【线段树】【4-6组队赛】Problem H
- 社説 20150409 日銀異次元緩和 「物価2%」の達成を焦るな
- Magento 用代码批量 添加产品的评论review(通过SKU)
- Windows和Linux下获取当前可执行文件路径和工作目录
- 人民日报:不告密不揭发是道德底线
- OPENGL 绘制基本图元