数据结构应用题第三章栈和队列代码c

  • 若希望循环队列中的元素都得到利用,则需要设置一个标志域tag,并且以tag的值为0或1来区分队头指针front和队尾指针rear相同的队列状态是“空”还是“满”
#ifndef T1_H
#define T1_H

#include<stdio.h>
#include<stdbool.h>
#include<stdlib.h>

#define MaxSize 10//定义栈中元素的最大个数

typedef int ElemType;
typedef struct{
    ElemType data[MaxSize];
    int front,rear;//front指向队头元素,rear指向队尾的下一个位置(也就是下一个应该插入的位置
    int tag;//0表示出队操作,1表示入队操作,只有在指针相同且是出队操作才表示空,在指针相同的入队操作表示满
}SqQueue;

void InitSqQueue(SqQueue *Q);//初始化
bool EnSqQueue(SqQueue *Q,ElemType x);//入队操作
bool DeSqQueue(SqQueue *Q,ElemType *x);//出队操作

#endif
#include "t1.h"

void InitSqQueue(SqQueue *Q){
    (*Q).rear=(*Q).front=0;
    (*Q).tag=0;
}
bool EnSqQueue(SqQueue *Q,ElemType x){
    if((*Q).rear==(*Q).front&&(*Q).tag==1)//队列满
        return false;

    (*Q).data[(*Q).rear]=x;
    (*Q).rear=((*Q).rear+1)%MaxSize;
    (*Q).tag=1;
    return true;
}
bool DeSqQueue(SqQueue *Q,ElemType *x){
    if((*Q).rear==(*Q).front&&(*Q).tag==0)//队空
        return false;

    (*Q).tag=0;
    *x=(*Q).data[(*Q).front];
    (*Q).front=((*Q).front+1)%MaxSize;
    return true;
}
void printfSqQueue(SqQueue Q){
    if(Q.rear==Q.front&&Q.tag==0)
        return;

    do{
        printf("%d<-",Q.data[Q.front]);
        Q.tag=0;
        Q.front=(Q.front+1)%MaxSize;
    }while(Q.rear!=Q.front&&Q.tag==0);
    printf("\n");
}
void test1(){
    SqQueue Q;
    InitSqQueue(&Q);
    
    ElemType x=0;
    scanf("%d",&x);
    while(x!=999){
        EnSqQueue(&Q,x);
        scanf("%d",&x);
    }
    // printf("%d-%d\n",Q.front,Q.rear);
    printfSqQueue(Q);
    DeSqQueue(&Q,&x);
    printfSqQueue(Q);
}
void main(){
    test1();
}
  • 假设一个算数表达式中包括圆括号,方括号和花括号三种类型的括号,编写一个算法来判别表达式中的括号是都匹配,以字符"\0"作为算数表达式的结束符

思路:遇到左括号入栈
遇到有括号,出栈匹配,同一类型括号且左右括号匹配成功,其他失败
全部匹配成功且栈为空,匹配成功

#ifndef LISTACK_H
#define LISTACK_H
#include<stdio.h>
#include<stdbool.h>
#include<stdlib.h>
// 链栈,不带头结点的情况
typedef char ElemType;
typedef struct LinkNode{
    ElemType data;//数据域
    struct LinkNode *next;//这里的定义是有问题的,在栈中应该设计一个top指针,但是考虑到手比脑快代码都写完了就不改了,介意的话把next改名为top就可以了
}LinkNode,*LinkStack;

bool InitStack4(LinkStack *s);//初始化不带头结点的栈
bool Push4(LinkStack *s,ElemType x);//入栈
bool Pop4(LinkStack *s,ElemType *x);//出栈
void printfStack4(LinkStack s);//打印
bool EmptyStack4(LinkStack s);//空栈
#endif
#include "listack.h"


bool InitStack4(LinkStack *s){
    *s=NULL;//栈空,不带头结点
    return true;
}
bool EmptyStack4(LinkStack s){
    if(s==NULL){
        return true;
    }
    return false;
}
bool Push4(LinkStack *s,ElemType x){
    LinkNode *p=(LinkNode *)malloc(sizeof(LinkNode));
    if(p==NULL)
        return false;
    p->data=x;
    // 这一步很容易错
    p->next=(*s);
    (*s)=p;
    return true;
}
bool Pop4(LinkStack *s,ElemType *x){
    if((*s)==NULL)//空表
        return false;
    LinkNode *p=*s;
    *s=(*s)->next;
    *x=p->data;
    free(p);

    return true;
}
void printfStack4(LinkStack s){
    // s=NULL;
    LinkNode *p=s;
    while(p!=NULL){
        printf("%c->",p->data);
        p=p->next;
    }
    printf("\n");
}
// void test4(){
//     LinkStack s;
//     InitStack4(&s);
//     // printfStack4(s);
//     Push4(&s,1);
//     Push4(&s,2);
//     printfStack4(s);
//     ElemType x=0;
//     Pop4(&s,&x);
//     printfStack4(s);

// }
// void main(){
//     test4();
// }
#include "listack.h"
// 假设字符串中只有三种括号 {} [] ()
bool ifMatch(char c[],int len){
    if(len==0)
        return true;

    LinkStack s;
    InitStack4(&s);
    for(int i=0;i<len;i++){
        if(c[i]=='{'||c[i]=='('||c[i]=='['){//左括号入栈
            Push4(&s,c[i]);
        }else if(c[i]=='}'||c[i]==')'||c[i]==']'){
            if(EmptyStack4(s))//如果是右括号需要被匹配但是栈空,直接返回false
                return false;
            char temp=' ';
            Pop4(&s,&temp);
            if(c[i]=='}'&&temp!='{')
                return false;
            else if(c[i]==']'&&temp!='[')
                return false;
            else if(c[i]==')'&&temp!='(')
                return false;   
        }
    }
    if(!EmptyStack4(s))//所有都正常匹配,但是左括号还有多余的
        return false;

    return true;

}


  • 车厢调度,两个铁道之间都是单向行驶道,火车调度站有一个用于调度的“栈道”,火车调度站的入口有n节硬座和软座车厢,(分别用H和S表示)等待调度,编写算法,输出对这n节车厢进行调度的操作序列,使得所有软座车厢都被调整到硬车厢之前。
    体会数组和指针之间的联系
#include "t2.h"

// 函数声明
bool InitStack4(LinkStack *s);//初始化不带头结点的栈
bool Push4(LinkStack *s,ElemType x);//入栈
bool Pop4(LinkStack *s,ElemType *x);//出栈
void printfStack4(LinkStack s);//打印
bool EmptyStack4(LinkStack s);//空栈

void train(char *train){
    char *p=train,*q=train,c=' ';
    LinkStack s;
    InitStack4(&s);
    while(*p){
        if(*p=='H')
            Push4(&s,*p);
        else
            *(q++)=*p;

        p++;
    }
    while(!EmptyStack4(s)){
        Pop4(&s,&c);
        *(q++)=c;
    }
}
void test2(){
    char c[]="HHHHSSSSSHSHSHSH";
    train(c);
    int index=0;
    while(c[index]!='\0'){
        printf("%c",c[index++]);
    }
}
void main(){
    test2();
}
bool InitStack4(LinkStack *s){
    *s=NULL;//栈空,不带头结点
    return true;
}
bool EmptyStack4(LinkStack s){
    if(s==NULL){
        return true;
    }
    return false;
}
bool Push4(LinkStack *s,ElemType x){
    LinkNode *p=(LinkNode *)malloc(sizeof(LinkNode));
    if(p==NULL)
        return false;
    p->data=x;
    // 这一步很容易错
    p->next=(*s);
    (*s)=p;
    return true;
}
bool Pop4(LinkStack *s,ElemType *x){
    if((*s)==NULL)//空表
        return false;
    LinkNode *p=*s;
    *s=(*s)->next;
    *x=p->data;
    free(p);

    return true;
}
void printfStack4(LinkStack s){
    // s=NULL;
    LinkNode *p=s;
    while(p!=NULL){
        printf("%c->",p->data);
        p=p->next;
    }
    printf("\n");
}
// void test4(){
//     LinkStack s;
//     InitStack4(&s);
//     // printfStack4(s);
//     Push4(&s,'1');
//     Push4(&s,'2');
//     printfStack4(s);
//     ElemType x=0;
//     Pop4(&s,&x);
//     printfStack4(s);

// }
// void main(){
//     test4();
// }
  • 某汽车轮渡口,过江渡船每次能载10辆车过江,过江车辆分为客车类和货车类,上渡船有如下规定:同类车先上船,客车先于货车上船,且每上4辆客车才允许上一辆货车,若等待的客车不足4辆,则以或车代替,若无货车等待,允许客车都上船。使设计算法模拟以上渡口管理。

思路:这里设计一种最大长度为10的队列,用Q存储要过车的顺序,QH表示货车的队列,QK表示客车队列,每次对过车的车辆先分类,对于客车,每4辆客车加一辆货车,然后对应balance标志位置0,客车空或者货车空就可把剩下的另一种类型车全部入Q队列,这里值得注意的是,因为设计的队列长度为10,所以对于大于10的车辆不会入队列。

#ifndef T1_H
#define T1_H

#include<stdio.h>
#include<stdbool.h>
#include<stdlib.h>

#define MaxSize 10//定义栈中元素的最大个数

typedef char ElemType;
typedef struct{
    ElemType data[MaxSize];
    int front,rear;//front指向队头元素,rear指向队尾的下一个位置(也就是下一个应该插入的位置
    int tag;//0表示出队操作,1表示入队操作,只有在指针相同且是出队操作才表示空,在指针相同的入队操作表示满
}SqQueue;

void InitSqQueue(SqQueue *Q);//初始化
bool EnSqQueue(SqQueue *Q,ElemType x);//入队操作
bool DeSqQueue(SqQueue *Q,ElemType *x);//出队操作
void printfSqQueue(SqQueue Q);//打印队列
bool EmptySqQueue(SqQueue Q);//判断队列是否为空
bool FullSqQueue(SqQueue Q);//队列是否满
#endif
#include "t1.h"

// 若希望循环队列中的元素都得到利用,则需要设置一个标志域tag,并且以tag的值为0或1来区分
// 队头指针front和队尾指针rear相同的队列状态是“空”还是“满”
void InitSqQueue(SqQueue *Q){
    (*Q).rear=(*Q).front=0;
    (*Q).tag=0;
}
bool EnSqQueue(SqQueue *Q,ElemType x){
    if((*Q).rear==(*Q).front&&(*Q).tag==1)//队列满
        return false;

    (*Q).data[(*Q).rear]=x;
    (*Q).rear=((*Q).rear+1)%MaxSize;
    (*Q).tag=1;
    return true;
}
bool DeSqQueue(SqQueue *Q,ElemType *x){
    if((*Q).rear==(*Q).front&&(*Q).tag==0)//队空
        return false;

    (*Q).tag=0;
    *x=(*Q).data[(*Q).front];
    (*Q).front=((*Q).front+1)%MaxSize;
    return true;
}
bool EmptySqQueue(SqQueue Q){
    if(Q.rear==Q.front&&Q.tag==0){
        return true;
    }
    return false;
}
bool FullSqQueue(SqQueue Q){
    if(Q.rear==Q.front&&Q.tag==1)
        return true;
    return false;
}
void printfSqQueue(SqQueue Q){
    if(Q.rear==Q.front&&Q.tag==0)
        return;

    do{
        printf("%c<-",Q.data[Q.front]);
        Q.tag=0;
        Q.front=(Q.front+1)%MaxSize;
    }while(Q.rear!=Q.front&&Q.tag==0);
    printf("\n");
}
// void test1(){
//     SqQueue Q;
//     InitSqQueue(&Q);
    
//     ElemType x=0;
//     scanf("%d",&x);
//     while(x!=999){
//         EnSqQueue(&Q,x);
//         scanf("%d",&x);
//     }
//     // printf("%d-%d\n",Q.front,Q.rear);
//     printfSqQueue(Q);
//     DeSqQueue(&Q,&x);
//     printfSqQueue(Q);
// }
// void main(){
//     test1();
// }
#include  "t1.h"

// K表示客车,H表示货车,QH用来存暂时还不能上船的货车,QK表示暂时还不能上船的货车,Q表示上船的顺序

void boat(char *c){
    if(*c=='\0')
        return;
    SqQueue Q;
    SqQueue QK;
    SqQueue QH;
    int balance=0;//表示当前客车已入船的数量,每4归0
    char temp=' ';//临时变量
    InitSqQueue(&Q);
    InitSqQueue(&QK);
    InitSqQueue(&QH);
    while(*c&&!FullSqQueue(QH)&&!FullSqQueue(QK)){//分类,是什么车
        if(*c=='H'){
            EnSqQueue(&QH,*c);
        }else{
            EnSqQueue(&QK,*c);
        }
        c++;
    }
    while(!EmptySqQueue(QK)||!EmptySqQueue(QH)){
        while(balance<4&&!EmptySqQueue(QK)){
            DeSqQueue(&QK,&temp);
            EnSqQueue(&Q,temp);
            balance++;
        }
        if(balance==4&&!EmptySqQueue(QH)){
            DeSqQueue(&QH,&temp);
            EnSqQueue(&Q,temp);
            balance=0;
        }
        while(EmptySqQueue(QK)&&!EmptySqQueue(QH)){
            DeSqQueue(&QH,&temp);
            EnSqQueue(&Q,temp);
        }
        while(EmptySqQueue(QH)&&!EmptySqQueue(QK)){
            DeSqQueue(&QK,&temp);
            EnSqQueue(&Q,temp);
        }
    }
    printfSqQueue(Q);
}
void test4(){
    char c[]="HHHHHHHHHHH";
    boat(c);
}
void main(){
    test4();
}
  • 1
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值