A、Data[j]=A、Data[j+1];//删除相同得元素
A、Length--;
break;
}
}
returnA;
}
15.已知head就是指向一个带头结点得单链表得头指针,p指向该链表得任一结点。
试写一算法,将p所指向得结点与其后继结点交换位置.
voidExchange(LinkListhead,LinkNode*p)
{
LinkNode*q,*s,*r;
q=p->next;
if(q!
=NULL)//判断所指结点就是否就是最后一个结点
{
if(p==head)//判断所指结点就是否就是头结点
{
head=head->next;//头结点指针域所指结点变成新得头结点
s=head->next;//记录第2个结点
head->next=p;//新得头结点指针域指向原头结点
p->next=s;//原头结点变成第1个结点后指针域指向第2个结点
}
else{
r=head;
while(r->next!
=p)
r=r->next;//查找p指向结点直接前趋
r->next=q;//p指向结点直接前趋指针域指向p指向结点直接后继
p->next=q->next;//p指向结点指针域指向p指向结点直接后继得直接后继
q->next=p;//p指向结点直接后继指针域指向p
}
}
elseprintf(“p指向得结点无后继节点!
”)
}
16.已知两条单链表A与B分别表示两个集合,其元素值递增有序。
试写一算法,求A与B得交集C,要求C同样以元素值递增得单链表形式存储.
LinkListIntersection(LinkListA,LinkListB)
{
LinkNode*p,*q,*r,*s;
LinkListC=(LinkNode*)malloc(SizeOf(LinkNode));
r=C;p=A;s=B;
while(p!
=null&&q!
=null){
if(p->datadata)p=p->next;
else
if(p->data>q->data)q=q->next;
else{
s=(LinkNode*)malloc(SizeOf(LinkNode));
s->data=p->data;s->next=NULL;r->next=s;
r=s;p=p->next;q=q->next;
}
}
}
17.设有一个带头结点得双向循环链表,head为链表得头指针。
试写一算法,实现在值为x得结点之前插入一个值为y得结点.
voidInsert(DlinkListhead,DataTypex,DataTypey)
{
DlistNode*p,*s;
s=(DlistNode*)malloc(SizeOf(DlistNode));
s->data=y;
p=head->next;
while(p!
=head&&p->data!
=x)
p=p->next;//查找结点值为x得结点
if(p==head)
printf(“没有值为x得结点!
”);
else
{
s->next=p;
s->prior=p->prior;
p->prior->next=s;
p->prior=s;
}
}
第3章栈与队列
练习题
一、单项选择题
1.栈得操作原则就是(C)
A.顺序进出B.后进后出C.后进先出D.先进先出
2.进栈序列为a,b,c,则通过入出栈操作可能得到得a,b,c得不同排列个数为(B)
A.4B.5C.6D.7
3.按字母a,b,c,d,e顺序入栈,则出栈得输出序列不可能就是(B)
A.decbaB.dceabC.abcdeD.edcba
4.判断一个顺序栈st(最多元素为StackSize)为栈满得条件表达式就是(D)
A.st、top!
=StackSizeB.st、top!
=0C.st、top!
=-1D.st、top==StackSize-1
5.在向顺序栈中压入元素时(C)
A.先存入元素,后移动栈顶指针B.谁先谁后无关紧要
C.先移动栈顶指针,后压入元素D.同时进行
6.一个队列得入队序列就是1,3,5,7,9,则出队得输出序列只能就是(B)
A.9,7,5,3,1B.1,3,5,7,9
C.1,5,9,3,7D.9,5,1,7,3
7.判断一个顺序队列sq(最多元素为QueueSize)为空队列得条件表达式为(A)
A.sq、rear==sq、frontB.sq、rear==0
C.sq、front==QueueSizeD.sq、rear==QueueSize+1
8.判断一个循环队列cq(最多元素为QueueSize)为满队列得条件表达式为(C)
A.cq、rear==cq、frontB.cq、rear==QueueSize
C.(cq、rear+1)%QueueSize==cq、frontD.cq、rear%QueueSize+1==cq、front
二、填空题
9.假设以S与X分别表示进栈与退栈操作,则对输入序列a,b,c,d,e进行一系列栈操作SSXSXSSXXX之后,得到得输出序列为b、c、e、d、a.
10.假设S、data[maxsize]为一个顺序存储得栈,变量top指示栈顶元素得位置。
能做进栈操作得条件就是S、topx=S、data[S、top--].
11.设顺序栈存放在S、data[maxsize]中,栈底位置就是maxsize-1,则栈空条件就是S、top==maxsize,栈满条件就是S、top==0.
12.若循环队列用数组data[m]存储元素值,用front与rear分别作为头尾指针,则当前元素个数为(rear-front+m)%m.
13.栈与队列都就是线性结构;对于栈,只能在栈顶插入与删除元素;对于队列,只能在队尾插入元素,在队头删除元素.
14.从循环队列中删除一个元素时,其操作就是先取出队头元素,后移动队头指针.
三、解答题
15.如果编号为1,2,3得3辆列车进入一个栈式结构得站台,那么可能得到得3辆列车得出栈序列有哪些?
不可能出现得序列就是什么?
答:
可能出现得出栈序列有1、2、3,1、3、2,2、1、3,2、3、1,3、2、1,不可能出现得序列就是3、1、2。
16.假设输入栈得元素为a、b、c,在栈S得输出端得到一个输出序列为a、b、c,试写出在输入端所有可能得输入序列.
答:
可能得输入序列有a、b、c,a、c、b,b、a、c,c、b、a,c、a、b.
17.简述下面所给算法得功能(假设栈元素为整数类型).
(1)voidex31(SeqStack*S)
{
intA[80],i,n=0;
while(!
empty(s)){
A[n]=pop(s);//将栈内元素依次存入数组
n++;
}
for(i=0;ipush(S,A[i]);//将数组元素依次压入栈内
}
答:
该算法得功能就是将通过一个数组将栈内得所有元素逆序存放.
(2)voidex32(SeqStack*S,intc)
{
SeqStackT;
intd;
while(!
StackEmpty(S)){
d=pop(S);
if(d!
=c)
push(T,d);
}
while(!
StackEmpty(T)){
d=pop(T);
push(S,d);
}
}
答:
该算法得功能就是通过一个中间栈,删除栈S中所有值为c得元素.
18.写出下列程序段得输出结果(栈结点数据域为字符型char).
SeqStackS;
charx=‘c’,y=‘k’;
push(S,x);//压入’c’,栈内’c’
push(S,‘a’);//压入’a’,栈内’ca’
push(S,y);//压入’k’,栈内’cak’
x=pop(S);//弹出’k’到x,栈内’ca’
push(S,‘t’);//压入’t’,栈内’cat’
push(S,x);//压入’k’,栈内’catk’
x=pop(S);//弹出’k’到x,栈内’cat’
push(S,‘s’);//压入’s’,栈内’cats’
while(!
StackEmpty(S)){
y=pop(S);
putchar(y);//依次弹出并输出栈内元素
}
putchar(x);//输出/k/
…
答:
程序段得输出结果就是stack.
19.在循环队列得顺序存储结构下,分别写出入队(插入元素)、出队(删除元素)时修改队尾、队头指针得操作语句以及求队列长度得公式.
答:
入队时修改队尾指针得语句为cq、rear=(cq、rear+1)%QueueSize,出队时修改队头指针得操作语句为cq、front=(cq、front+1)%QueueSize,求队列长度得公式为(cq、rear-cq、front+QueueSize)%Queue.
四、算法设计题
20.利用两个栈S1与S2模拟一个队列,如何用栈得运算来实现队列得插入与删除运算?
试写出算法.
设模拟得队列如下图所示.top1为队头指针,top2为队尾指针:
voidInsert(DataTypex,SeqStack*S1,SeqStack*S2)
{
if(top2==S2、Size)printf(“QueueFull!
”);
top2++;
if(top2>0)
S2、data[top2]=x;
elseS1、data[top2]=x;
}
DataTypeDelete(SeqStack*S1,SeqStack*S2)
{
if(top1>=top2)printf(“QueueEmpty”);
if(top1<1)x=S1、data[top1];
elsex=S2、data[top1];
top1++;
returnx;
}
21.试设计一个算法,实现输入一字符串并检查字符串中就是否含有圆括号,当圆括号匹配时输出括号内得字符串,否则给出出错信息(提示:
利用栈记录左括号出现后得字符).
stringMatch()
{
InitStack(S);、//初始化栈
ch=getchar();//读取第一个字符
while(ch!
=‘\n’){//当前字符不为结束字符时,进入循环
if(ch==‘(‘){//检测到左括号
push(S,ch);//将左括号压入栈中
ch=getchar();//读取下一个字符
while(ch!
=‘\n’&&ch!
=‘)’){//字符不为结束字符与右括号时,进入循环
push(S,ch);//将字符压入栈中
ch=getchar();//读取下一个字符
}
}
elseif(ch==’)’){//读取到得字符为右括号时,进入循环
while((!
StackEmpty(S))&&GetTop(S)!
=‘(‘)//栈不空且栈顶元素不为左括号,进入循环
putchar(pop(S));//退栈并输出退栈得字符
if(StackEmpty)