2021-06-20数据结构实验1预习

**

图书信息管理系统预习报告

**
要求:
设计并实现一个图书信息管理系统。根据实验要求设计该系统的菜单和交互逻辑,并编码实现增删改查的各项功能。 该系统至少包含以下功能:(1) 根据指定图书个数,逐个输入图书信息;(2) 逐个显示图书表中所有图书的相关信息;(3) 能根据指定的待入库的新图书的位置和信息,将新图书插入到图书表中指定的位置;(4) 根据指定的待出库的旧图书的位置,将该图书从图书表中删除;(5) 能统计表中图书个数;(遍历)(6) 实现图书信息表的图书去重;(7) 实现最爱书籍查询,根据书名进行折半查找,要求使用非递归算法实现,成功返回此书籍的书号和价格;(8) 图书信息表按指定条件进行批量修改;(9) 利用快速排序按照图书价格降序排序;实现最贵图书的查找;

相应功能实现:

cout << " 1.插入数据(逻辑位置,>0)" << endl;

template < class T >
void SeqList<T>::Insert(int i, T x) {
 if (length >= MaxSize) cout<< "上溢"<<endl;
 if (i<1 || i>length + 1) cout<< "位置错误"<<endl;
 for (int j = length; j >= i; --j) {  //遍历调整元素位置; 
  data[j] = data[j - 1];
 }
 data[i - 1] = x;//同时改变length
 ++length;
}

cout << " 2.删除某数据(逻辑位置,>0)" << endl;

template < class T >
T SeqList<T>::Delete(int i) {
 if (length == 0) cout << "下溢" << endl;
 if (i<1 || i>length) cout<< "位置错误"<<endl;
 T x = data[i - 1];
 for (int j = i; j < length; ++j) {
  data[j - 1] = data[j]; //删除的元素后的元素全部前移动一位,以达到删除的目的; 
 }
 --length;//同时改变length
 return x;
}

cout << " 3.查找某数据(逻辑位置,>0)" << endl;

template < class T >
void PrintSd(T s) {  //输出指定位置元素; 
 cout << "书号         书名       价格" << endl;
 cout << "----------------------------" << endl;
 cout << s.no << setw(9) << s.name << setw(9) << s.price << endl;
 cout << "----------------------------" << endl;
}

cout << " 4.输出所有数据" << endl;



template < class T >
void PrintList(SeqList<T> d) { //全部输出; 
 cout << "       书数: "<<d.GetLength() << endl;
 
 if (d.GetLength() > 0) {//有书输出
  cout << "书号        书名       价格" << endl;
  cout << "----------------------------" << endl;
  for (int i = 1; i <= d.GetLength(); ++i) {
   Book s = d.Get(i);
   cout << s.no << setw(9) << s.name << setw(9) << s.price << endl;
  }
  cout << "----------------------------" << endl;
 }
 else {//无书
  cout << "无记录" << endl;
 }
}

cout << " 5.输出数据数量" << endl;

int GetLength() { return length; }  //求顺序表的长度

cout << " 6.书号去重 " << endl;

template < class T >
void SeqList<T>::RpDelete() {
 for (int i = 0; i <=length; ++i) {//双重循环
  for(int j=i+1;j <=length;++j)
   if (data[i].no==data[j].no) {
    Delete(j+1);
   }
 }
 cout << "     去重成功!" << endl;
}

cout << " 7.书名二分查找" << endl;

template < class T >
int SeqList<T>::BiSearch(string x) {
 int low = 0;
 int high = length - 1;
 int mid = 0;
 double key = 0;//查找依据
 for (int i = 0; i < length - 1; i++) {//书名转化价格查找
  if (data[i].name == x) {
   key = data[i].price;
  }
 }
 while (low <= high) {//逐步缩小范围
  mid = (low + high) / 2;
  if (data[mid].price > key)
   low = mid + 1;
  else if (data[mid].price < key)
   high = mid - 1;
  else
   return mid;
 }
 return -1;
}

cout << " 8.批量修改" << endl;

template < class T >
void SeqList<T>::Adjust() {
 double sum = 0;//求和
 for (int i = 0; i < length-1; ++i) {
  sum += data[i].price;
 }
 double ave = sum / (length-1);//求平均
 //调整
 for (int i = 0; i < length-1 ; ++i) {
  if (data[i].price < ave) {
   data[i].price += 0.2 * data[i].price;  }else {
   data[i].price += 0.1 * data[i].price;
  }
 }
 cout << "平均价格" << ave << endl;
 
}

cout << " 9.快排" << endl;

template < class T >
void SeqList<T>::QuickSort(int low,int high){
 if(low<high)  //递归终止条件
 { 
  int i = low, j = high;
   T x = data[low];                                     
  while(i<j)  {    
  	while(i<j && data[j].price <= x.price) j--;  //先从右边开始    
  	if(i<j) data[i++]= data[j];      
  	while(i<j && data[i].price >= x.price) i++;     if(i<j) data[j--]= data[i];    } 
     	data[i] = x;  //i已经排列好  QuickSort(low ,i-1);//递归  
  	QuickSort(i+1 ,high); 
  }
}

主函数用了文件流:
效果截图:
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述在这里插入图片描述在这里插入图片描述

在这里插入图片描述

在这里插入图片描述在这里插入图片描述
在这里插入图片描述
总结:
代码由一个结构体Book,一个SeqList类,一个主函数组成;主函数用了一个文件流输入,当然也可不用,用插入函数输入数据;书名二分查找要先把书名转化为书价,再快速排序书价,再二分查找书价;快速排序注意先右边遍历;我把结构体Book中的两个char数组改用了string变量;

完整代码:

#include<iostream>
#include<string>
#include<fstream>
#include<iomanip>
#include<algorithm>
using namespace std;
#define MaxSize 100 


typedef struct {
	string no;   //书号
	string name; //书名
	double price;     //价格
}Book;

template < class T >
class SeqList
{
public:
	SeqList() { length = 0; }       //无参构造函数
	SeqList(T a[], int n);       //有参构造函数
	~SeqList();             //析构函数为空
	int GetLength() { return length; }  //求顺序表的长度
	T Get(int i);  //取顺序表的第i个元素(i为逻辑号)
	void Insert(int i, T x);  //在顺序表中第i个位置插入值为x的元素(i为逻辑号)
	T Delete(int i);//删除顺序表的第i个元素(i为逻辑号)
	void RpDelete();//去重
	int BiSearch(string x);//书名二分查找
	void Adjust();//价格调整
	void QuickSort(int low, int high);//价格降序排列
private:
	T data[MaxSize];      //存放书数据的数组
	int length;            //顺序表的长度
};

template < class T >
SeqList<T>::SeqList(T a[], int n) { //有参构造函数
	if (n > MaxSize) cout << "参数错误" << endl;
	for (int i = 0; i < n; ++i) {
		data[i] = a[i];
	}
	length = n;//初始化
}

template < class T >
T SeqList<T>::Get(int i) { //取顺序表的第i个元素
	if (i > 0 && i <= length) //保证i不会引起数组overflow; 
		return data[i - 1];

}

template < class T >
void SeqList<T>::Insert(int i, T x) {
	if (length >= MaxSize) cout << "上溢" << endl;
	if (i<1 || i>length + 1) cout << "位置错误" << endl;
	for (int j = length; j >= i; --j) {  //遍历调整元素位置; 
		data[j] = data[j - 1];
	}
	data[i - 1] = x;//同时改变length
	++length;
}


template < class T >
T SeqList<T>::Delete(int i) {
	if (length == 0) cout << "下溢" << endl;
	if (i<1 || i>length) cout << "位置错误" << endl;
	T x = data[i - 1];
	for (int j = i; j < length; ++j) {
		data[j - 1] = data[j]; //删除的元素后的元素全部前移动一位,以达到删除的目的; 
	}
	--length;//同时改变length
	return x;
}

template < class T >
void SeqList<T>::RpDelete() {
	for (int i = 0; i <= length; ++i) {//双重循环
		for (int j = i + 1; j <= length; ++j)
			if (data[i].no == data[j].no) {
				Delete(j + 1);
			}
	}
	cout << "     去重成功!" << endl;
}


template < class T >
int SeqList<T>::BiSearch(string x) {
	int low = 0;
	int high = length - 1;
	int mid = 0;
	double key = 0;//查找依据
	for (int i = 0; i < length - 1; i++) {//书名转化价格
		if (data[i].name == x) {
			key = data[i].price;
		}
	}
	while (low <= high) {//逐步缩小范围
		mid = (low + high) / 2;
		if (data[mid].price > key)
			low = mid + 1;
		else if (data[mid].price < key)
			high = mid - 1;
		else
			return mid;
	}
	return -1;
}

template < class T >
void SeqList<T>::Adjust() {
	double sum = 0;//求和
	for (int i = 0; i < length - 1; ++i) {
		sum += data[i].price;
	}
	double ave = sum / (length - 1);//求平均
	//调整
	for (int i = 0; i < length - 1; ++i) {
		if (data[i].price < ave) {
			data[i].price += 0.2 * data[i].price;

		}
		else {
			data[i].price += 0.1 * data[i].price;
		}
	}
	cout << "平均价格" << ave << endl;

}

template < class T >
void SeqList<T>::QuickSort(int low, int high) {
	if (low < high)  //递归进入条件
	{

		int i = low, j = high;

		T x = data[low];

		while (i < j) {

			while (i < j && data[j].price <= x.price) j--;  //先从右边开始

			if (i < j) data[i++] = data[j];

			while (i < j && data[i].price >= x.price) i++;

			if (i < j) data[j--] = data[i];

		}
		data[i] = x;  

		QuickSort(low, i - 1);  
		QuickSort(i + 1, high);

	}
}


template < class T >
SeqList<T>::~SeqList() {

}




template < class T >
void PrintList(SeqList<T> d) { //全部输出; 
	cout << "       书数: " << d.GetLength() << endl;

	if (d.GetLength() > 0) {//有书输出
		cout << "书号        书名       价格" << endl;
		cout << "----------------------------" << endl;
		for (int i = 1; i <= d.GetLength(); ++i) {
			Book s = d.Get(i);
			cout << s.no << setw(9) << s.name << setw(9) << s.price << endl;
		}
		cout << "----------------------------" << endl;
	}
	else {//无书
		cout << "无记录" << endl;
	}
}


template < class T >
void PrintSd(T s) {  //输出指定位置元素; 
	cout << "书号         书名       价格" << endl;
	cout << "----------------------------" << endl;
	cout << s.no << setw(9) << s.name << setw(9) << s.price << endl;
	cout << "----------------------------" << endl;
}




int main() {
	ifstream f;//调用外部文件;
	int w;//键盘输入的数据位置;
	int op; //switch选case的凭依; 
	Book tem; // 辅助SeqList<Sd> s的函数Insert()使用; 
	SeqList<Book> s;//定义顺序表对象; 
	char ny; //辅助选y或n用;
	string na;//辅助输入名字;
	int whi = 1; //菜单进入和跳出的条件;
	int wh = 1;//菜单case1循环输入;
	cout << "使用已有的数据输入:y或者不使用输入:n" << endl;
	cin >> ny;
	while (1) {//文件流
		if (ny == 'y') {
			f.open("书.txt", ios::in);
			if (!f) {
				cout << "不存在文件书.txt" << endl;
				continue;
			}
			else {
				cout << "存在文件书.txt" << endl;
				int i = 0;
				while (!f.eof()) {
					f >> tem.no >> tem.name >> tem.price;
					s.Insert(i + 1, tem);
					++i;
				}
			}
			f.close();
			break;
		}
		else if (ny == 'n') {
			break;
		}
	}

	while (whi) {
		cout << "     主菜单      " << endl;
		cout << "     1.插入数据(逻辑位置,>0)" << endl;
		cout << "     2.删除某数据(逻辑位置,>0)" << endl;
		cout << "     3.查找某数据(逻辑位置,>0)" << endl;
		cout << "     4.输出所有数据" << endl;
		cout << "     5.输出数据数量" << endl;
		cout << "     6.书号去重         " << endl;
		cout << "     7.书名二分查找" << endl;
		cout << "     8.批量修改" << endl;
		cout << "     9.快排" << endl;
		cout << "     10.退出" << endl;
		cout << "     输入(1~10)         " << endl;
		cin >> op;
		switch (op) {
		case 1:
			while (wh) {
				cout << "请输入插入数据位置(逻辑位置,>0)" << endl;
				cin >> w;
				cout << "请输入书号,名字,价格" << endl;
				cin >> tem.no;
				cin >> tem.name;
				cin >> tem.price;
				s.Insert(w, tem);
				if (tem.price == 0) {//按要求退出插入;
					break;
				}
			}
			break;
		case 2:
			cout << "请输入删除数据位置(逻辑位置,>0)" << endl;//按位置删
			cin >> w;
			s.Delete(w);
			break;
		case 3:
			cout << "请输入查找数据位置(逻辑位置,>0)" << endl;//按名字查找
			cin >> w;
			PrintSd(s.Get(w));
			break;
		case 4:
			PrintList(s);
			break;
		case 5:
			cout << "数量:   " << s.GetLength() << endl;//数量
			break;
		case 6:
			s.RpDelete();//去重
			PrintList(s);
			break;
		case 7:
			s.QuickSort(0, s.GetLength() - 1);//二分查找先快排,因为二分只能在有序的元素队中找
			cout << "name:";
			cin >> na;
			PrintSd(s.Get(s.BiSearch(na) + 1));
			break;
		case 8:
			s.Adjust();//按要求的调整
			PrintList(s);
			break;
		case 9:
			s.QuickSort(0, s.GetLength() - 1);//快速排序,0, s.GetLength() - 1的输入方式必要,因为函数中要用到递归
			PrintList(s);
			break;
		case 10:
			whi = 0;//退出
		default:continue;
		}
	}

	return 0;
}
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值