博客作业03--栈和队列
一.学习总结(2分)
1.1 写出你认为本周学习中比较重要的知识点关键词,如逻辑结构、栈、队列、存储结构等。
1.1绪论:程序=数据结构+算法 数据组织方式:1数据的逻辑结构和数据的存储结构,逻辑结构:集合,线性结构,树形结构,图形结构,存储方式:顺序存储方式,链式存储方式,索引存储方式,散列存储方式(空间复杂度,时间复杂度)。
(逻辑结构)线性结构:链式存储方式+顺序存储方式。
顺序存储方式:操作:creatlist 产生顺序表(缺点:无法动态分配空间一开始就给了一个固定值可能造成空间的不足或者浪费)InitList(初始化顺序表时间复杂度o(n)),Destorylist(销毁链表,时间复杂度o(1),insertlist(插入顺序表时间复杂度o(n)),deletelist(时间复杂度(o(n))
链式存储方式(单链表,双链表,循环链表,有序表):creatlist 产生顺序表(优点:动态分配避免空间浪费),Destorylist(销毁链表,时间复杂度o(n)),insertlist(插入顺序表时间复杂度o(1)),deletelist(时间复杂度(o(1))找到某个元素:searchlist(时间复杂度s1)
有序表(按顺序排列的线性结构):优点在归并等等操作的时候十分便利。
以下是两种特殊的线性结构:
队(先进先出) 逻辑结构:线性结构 存储结构:顺序表存储,链表存储 操作:入队:push,出队:pop,产生队列creatqueue,销毁队列:Destoryqueue,取队头元素:getsqueue
栈 (后进先出)逻辑结构:线性结构 存储结构:顺序表存储,链表存储 操作:入栈:push,出栈:pop,产生队列creatstach,销毁队列:Destorystack,取栈顶元素元素:getstack
多用顺序存储的方式,但是这样的出队(或者栈)并没有真的消失。在计算多项式的后缀表达式,迷宫问题,银行排队问题等问题有大量的应用,在系统,函数调用,递归中也有大量的应用。
1.2 思维导图
二.PTA实验作业(4分)
2.1 题目1:7-4 列车厢调度
1. 设计思路
for(1号轨道不空)
{
if(1号轨道的轨道头结果要求序列匹配)
{
就让这节轨道到2,并让结果序列后移
}
else if{3号轨道轨道头和要求序列匹配){
就让这节轨道到2,并让结果序列后移}
else
{
就让1号轨道轨道头到3号轨道
}
}
for(3号轨道不空){
if(不能依次出轨)break;
}
if(1,3轨道是空)
空了输出结果
else
就输出那句话
2.代码截图
3.本题调试过程碰到问题及PTA提交列表情况说明。
就是3与2是否匹配的时候没有循环判断造成错误
题目2.7-3 银行排队问题之单队列多窗口服务
1.设计思路
for(当柜台不全空闲或者队伍不全空的时候){
将所有人入队并且保留所有人的信息;
while(到达队头出队的时间){
if(有柜台空闲){
让这个人出队,让柜台的状态变成有人了,并且保留处理人的信息
并且用现在的时间减去他来的时间计算这个人的等待时间,更新所有的要求输出
}
else 让时间继续增加,继续在队头待者}
让柜台中正在处理人处理时间减1;
if(有柜台的处理时间变成0)释放柜台
else continute;
}
输出要求输出的东西
2.代码截图
3.本题调试过程碰到问题及PTA提交列表情况说明。
没问题
题目3.7-7 银行排队问题之单队列多窗口加VIP服务
1.设计思路
if(vip柜台是空闲的)
那么就判断现在在队伍中已经来了的人之中去查询有没有vip,有的话让他先出来(用移动数组的方式),并且让这个柜台保留这个人的信息,
然后可以重复7-3的步骤
不同的是不能保留这个人在队列里面的编号(由于vip出队是真正意义上的出队)所以就只需要保留这个人的处理时间
2.代码截图
3.本题调试过程碰到问题及PTA提交列表情况说明。
三.截图本周题目集的PTA最后排名(3分)。
3.1 栈PTA排名
3.2 队列PTA排名
3.3 我的总分:310
四. 阅读代码(必做,1分)
题目类型: 数据结构, 链表
输入n个矩阵的维度和一些矩阵链乘的表达式,输出乘法的次数。如果乘法无法进行,输出error。假定A是mn矩阵,B是np矩阵,则乘法的次数为mnp。如果矩阵A的列数不等于矩阵B的行数,则这两个矩阵无法进行乘法运算。例如:A是5010的,B是1020的,C是205的,则 A(BC)的乘法次数为10205(BC的乘法次数)+5010*5(A(BC)的乘法次数)=3500.
要求:
第一行包括一个正整数n,表示共有n个矩阵参与运算。
接下来的n行,每行包括三部分,第一部分是矩阵的名字(一个大写字母),第二部分和第三部分各是一个正整数,分别表示该矩阵的行数和列数,这三部分之间有一个空格分隔。
最后一行包括一个矩阵运算的合法字符串(只包括小括号和上述矩阵的名称)
样例输入:
9
A 50 10
B 10 20
C 20 5
D 30 35
E 35 15
F 15 5
G 5 10
H 10 20
I 20 25
A
B
C
(AA)
(AB)
(AC)
(A(BC))
((AB)C)
(((((DE)F)G)H)I)
(D(E(F(G(HI)))))
((D(EF))((GH)I))
样例输出:
0
0
0
error
10000
error
3500
15000
40500
47500
15125
题目大意:
给出一系列的矩阵,给他们取名A ,B…… 以及它们的行数和列数。给完后,给出一系列的表达式,然后要求求出按这些表达式进行计算,会有多少次乘法步骤。
解体思路:
这题和括号匹配那题很像。关键的步骤是计算矩阵乘法次数的这个过程。
//解析表达式
#include<cstdio>
#include<stack>
#include<iostream>
#include<string>
using namespace std;
struct Matrix{
int a,b;
Matrix(int a=0,int b=0):a(a),b(b){
}
}m[26];
stack<Matrix> s;
int main()
{
int n;
cin>>n;//参与矩阵运算的数目
for(int i=0;i<n;i++)//将每个矩阵的行列数目填入结构体数组
{
string name;//定义矩阵的名字
cin>>name;
int k=name[0]-'A';//将矩阵名字转换成对应的数字
cin>>m[k].a>>m[k].b;//分别记录行列
}
string expr;//定义运算串
while(cin>>expr)
{
int len=expr.length();//定义len为运算串长度
bool error=false;
int ans=0;
for(int i=0;i<len;i++)
{
if(isalpha(expr[i])) s.push(m[expr[i]-'A']);//判断运算符表达式是不是字母,若是就去m数组的相应位置找寻数组信息,并让其入栈
else if(expr[i]==')') {//如果运算符是右括号
Matrix m2=s.top();//将s栈中的栈顶作为m2矩阵运算结构体的m2元素
s.pop();
Matrix m1=s.top();//将s栈中的栈顶作为m1矩阵运结构体的m1元素
s.pop();
if(m1.b!=m2.a){
error=true;break;//行列不匹配无法相乘,并跳出循环
}
ans+=m1.a*m1.b*m2.b;//计算得出结果
s.push(Matrix(m1.a,m2.b));//将m1里面的中的m1的,m2的列作为一个运算结果重新入录回s栈中
}
}
if(error) printf("error\n");//如果出现了error,则输出error
else printf("%d\n",ans);//否则输出结果
}
return 0;
}
本题巧妙的运用了栈先进后出的特点轻松的解决了这个看似很难的问题,熟练的运用了c++中的stl类,令人赞叹。