题干:

样例输入输出:

解题思路:

题目说的很清晰了,就是用两个栈模拟队列。这里最核心的思想就是要清楚栈和队列的特性是什么。其次,我们要选择一个栈作为输入栈一个作为输出栈,为什么???其实,如果只是为了模拟队列,我们不需要考虑很多,只需要满足先进先出的特性即可,不必区分哪个栈输入哪个栈输出。

比方说,我们可以:(这里定义s1为输入栈,s2为输出栈)

入队操作时

  1. 判断随意选择的输入栈s1是否为满,不满可以直接入栈
  2. 当s1满时,若s2为空,可以先将s1中的元素转移到s2中,然后s1入栈(这样做是为了不破坏数据的正确输入输出顺序,而如果s1满且s2不为空时,此时再入栈,就要将s1中的栈顶元素出栈并压入s2。但是,如果这样做,因为我们模拟的是队列,s2原来栈顶的元素本来应该作为队头元素首先出队,但是你这样压入了s1的元素,就完全破坏了队列的特性)
  3. 当s1满时,并且s2中不为空,则无法入栈(原因在2中已有说明)

出队操作时

  1. 当s2中有元素时可以直接出栈
  2. 当s2中为空时,将s1中的元素转移到s2中
  3. s1与s2都为空,则无法出栈  (出队操作逻辑比较简单)

这样子,我们就完成了这道题吗?

相信有同学和我一样,就这样提交上去,发现答案全错???

这里大家要注意的是,题目中要求的ERROR信息,这是一个很关键的地方,题目中所要求的队空和堆满ERROR都是在性能最优的情况先考虑的,也就是说我们上面的解决方法不是最优解,在我们的方法中队空队满都是假队空队满。如果换一种方法,还是可以放进去元素,或是元素出队的。

这里告诉大家,最优解就是,容量较小的作为输入栈s1,而容量大的则作为输出栈s2。这个原理其实并不难理解,大家仔细想想就理解了,这里就不赘述了。。。

最终代码如下:

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

typedef struct Stack{
    int *data;
    int top;
    int capacity;
}Stack;

Stack* createStack(int max){
    Stack *s = (Stack*)malloc(sizeof(Stack));
    s->data = (int*)malloc(max*sizeof(int));
    s->top = -1;
    s->capacity = max;
    return s;
}


int isFull(Stack *s){
    return s->top == s->capacity-1;
}

int isEmpty(Stack *s){
    return s->top == -1;
}

int Push(Stack *s,int item){
    if(isFull(s)) return 0;
    s->data[++(s->top)] = item;
    return 1;
}

int Pop(Stack *s,int *item){
    if(isEmpty(s)) return 0;
    *item = s->data[(s->top)--];
    return 1;
}


typedef struct{
    Stack *s1;
    Stack *s2;
    int capacity1;
    int capacity2;
}Queue;

Queue* initQueue(int n1,int n2){
    Queue *q = (Queue*)malloc(sizeof(Queue));
    q->s1 = createStack(n1);
    q->s2 = createStack(n2);
    q->capacity1 = n1;
    q->capacity2 = n2;
    return q;
}


void AddQ(Queue *q,int item){
    //当s1不为满时,直接入栈
    if(!isFull(q->s1)){
        Push(q->s1,item);
        return;
    }
    //当s1满时,若s2为空,可以先将s1中的元素转移到s2中,然后s1入栈
    if(isFull(q->s1) && isEmpty(q->s2)){
        int data;
        while(Pop(q->s1,&data)!=0){
            Push(q->s2,data);
        }
        Push(q->s1,item);
        return;
    }
    //当s1满时,并且s2中不为空,则无法入栈
    if(isFull(q->s1) == 1 && isEmpty(q->s2)!=1){
        printf("ERROR:Full\n");
        return;
    }
}

int Delete(Queue *q){
    //当s2中有元素时可以直接出栈
    if(isEmpty(q->s2)==0){
        int data;
        if(Pop(q->s2,&data) == 1){
            return data;
        }
    }
    //当s2中为空时,将s1中的元素转移到s2中
    if(isEmpty(q->s2)==1 && isEmpty(q->s1)!=1){
        int data;
        while(Pop(q->s1,&data)!=0){
            Push(q->s2,data);
        }
        Pop(q->s2,&data);
        return data;
    }
    if(isEmpty(q->s1)&&isEmpty(q->s2)){
        printf("ERROR:Empty");
        return 99999;
    }
}

int main(){

    char cmd;
    int num;
    int n1,n2;
    scanf("%d %d",&n1,&n2);
    int min,max;
    if(n1<n2){
        min = n1;
        max = n2;
    }else{
        min = n2;
        max = n1;
    }
    Queue *q = initQueue(min,max);
    getchar();
    while(scanf("%c",&cmd)==1&&cmd!='T'){
        if(cmd=='A'){
            scanf("%d",&num);
            AddQ(q,num);
        }
        if(cmd=='D'){
            int data = Delete(q);
            if(data!=99999){
                printf("%d\n",data);
            }
        }
    }
    return 0;
}


AC

Logo

北京人形旗下天工造物具身智能开源社区,聚焦具身天工与慧思开物两大平台

更多推荐