本章主要可能出小题、应用题,出算法题概率不是很大。
栈
基本概念
LIFO,很多都很熟悉了。但是,要知道它也算是一种线性表, 但是是操作受限(限制了存取点)的线性表。并且要知道,它和队列的逻辑结构,都是属于线性结构。
顺序栈
使用顺序表存储。(不会发生假溢出的现象)
删除时,是逻辑删除,并没有真正抹零。
共享栈
-
判空条件
top0 = = − 1 , top1==MaxSize − 1 \text{top0}==-1, \text{top1==MaxSize }-1 top0==−1,top1==MaxSize −1
-
判满条件
top0 − top1 = 1 \text{top0} - \text{top1} = 1 top0−top1=1
链栈
操作只能在单链表的表头进行,并且链栈没有头结点。
队列
基本概念
FIFO
顺序存储
发生“假溢出”,不能用 r e a r = = M a x S i z e − 1 rear == MaxSize -1 rear==MaxSize−1 来判断队列满。
循环队列⭐
循环队列的出现是为了克服上面的这个假溢出的现象。
循环队列千千万万,随题目而变,一定会有下面的规定:
- 入队是在队尾入队,要执行 Q . r e a r = ( Q . r e a r + 1 ) m o d M a x s i z e Q.rear = (Q.rear+1)\mod{Maxsize} Q.rear=(Q.rear+1)modMaxsize
- 队伍中的元素的个数: ( Q . r e a r − Q . f r o n t + M a x s i z e ) % M a x s i z e (Q.rear-Q.front +Maxsize)\%Maxsize (Q.rear−Q.front+Maxsize)%Maxsize
- 出队是在队首 f r o n t front front出队。而且出队的操作,是 Q . f r o n t = ( Q . f r o n t + 1 ) m o d M a x s i z e Q.front= (Q.front+1)\mod{Maxsize} Q.front=(Q.front+1)modMaxsize
不同样式的循环队列
- 浪费一个空间
- 判满条件 ( Q . r e a r + 1 + M a x s i z e ) % Q . f r o n t (Q.rear +1 +Maxsize)\%Q.front (Q.rear+1+Maxsize)%Q.front
- 增设数据成员
- size
- tag
链式存储
头指针,指向队头;尾指针,指向队尾。插入,利用队尾指针;删除,利用队头指针。
最适合的,是删除和插入都是 O ( 1 ) O(1) O(1).
双端队列
小题;一般不难。
应用
括号匹配
是可能考算法题的。思想是建立一个栈存放符号。将非括号的字符丢掉,见到一个左括号,便进栈;如果见到一个右括号,则弹出栈顶元素,并且查看是否匹配:【( — ), [ — ], { — }】。结束时,一定要查看栈还有没有元素,如果有,返回错误;反之则正确。
int Bracketscheck(SqStack *S,char *str)
{
InitStack(S);
char e;
int i=0;
while(str[i]!='\0')
{
switch(str[i]){
case '(':
Push(S,'(');
break;
case '{':
Push(S,'{');
break;
case '[':
Push(S,'[');
break;
case ')':
Pop(S,&e);
if(e!='(')
return 0;
break;
case '}':
Pop(S,&e);
if(e!='{')
return 0;
break;
case ']':
Pop(S,&e);
if(e!='[')
return 0;
break;
default:
break;
}
i++;
}
int h=StackEmpty(S);
if(h==1)
return 0;
else
return 1;
}
————————————————
版权声明:本文为优快云博主「lz846525719」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.youkuaiyun.com/lz846525719/article/details/82794989
栈的表达式求值
-
利用栈【栈里的,都是符号】
-
优先级
isp = 栈内优先数; icp = 栈外优先数(要进栈的优先)
isp(栈顶) < < < icp(待选符号),进栈
isp(栈顶) ≥ \ge ≥ icp(待选符号),出栈;并且,会导致栈顶起义。
-
口诀
乘除高加减,括号最痴情【括号匹配了,直接两个携手隐退江湖】。平起平坐,我先出去。【相同符号,栈内优先】
-
-
括号法
按照优先级,给每个单独加括号
然后将运算符号移动到括号的外边
然后去掉括号,只剩下运算符和运算数
-
树前后序遍历法
画成树,然后利用前后序遍历的路子来。
函数调用
利用栈实现非递归运算。
先构造一个栈,栈顶是第一个需要运算的数,栈底是我们最终要算得的结果。
// 核心部分 : 很精彩
while (top >= 0)
{
st [top]. val = f(fv1, fv2); // fv1 是第一个运算值,fv2 是第二个运算数
fv1 = fv2;
fv2 = st[top].val;
top--;
}
数组
对称矩阵的压缩存储
利用对称性,只存放上三角或者下三角。
要注意判断,所给的究竟是按上三角存还是下三角存;并且所给或者所要求的索引 a i j a_{ij} aij是否是上三角或者是下三角。
方法:先计算出前 i − 1 i-1 i−1行的元素的个数
下三角: i ( i − 1 ) 2 \frac{i(i-1)}{2} 2i(i−1)【A[1,N][1,N]】; i ( i + 1 ) 2 \frac{i(i+1)}{2} 2i(i+1)【A[0,N][0,N]】
上三角: ( 2 n − i + 2 ) ( i − 1 ) 2 \frac{(2n-i+2)(i-1)}{2} 2(2n−i+2)(i−1)【A[1,N][1,N]】; ( 2 n − i + 3 ) ( i ) 2 \frac{(2n-i+3)(i)}{2} 2(2n−i+3)(i)【A[0,N][0,N]】
再计算出前第几个元素
下三角:用 j j j直接算
上三角:【注意】此时是不可以直接加 j − 1 j-1 j−1或者 j j j,而是 i − j i-j i−j(因为有 i − 1 i-1 i−1个元素被忽略掉)
三对角矩阵
知 a i j a_{ij} aij求 k k k: k = 2 i + j − 3 k = 2i+j-3 k=2i+j−3