用两个队列(先进先出)实现一个栈(后进先出)
题目链接:https://leetcode.cn/problems/implement-stack-using-queues/description/
1.C语言首先要造一个队列出来
2.两个队列实现栈,始终保持一个队列为空,一个队列非空的状态
3.根据栈先进先出的特性,入栈要把数据放入非空队列中
4.取栈顶元素则取非空队列的队尾即可
5.出栈,并返回栈顶元素的值,则需要把非空队列中n个数据的前n-1个数据导入空队列中,剩下的唯一一个数据就是要出栈的数据。
cpp
typedef int QDataType;
typedef struct QueueNode
{
QDataType val;
struct QueueNode* next;
}QNode;
typedef struct Queue
{
QNode* phead;
QNode* ptail;
int size;
}Queue;
//初始化
void QueueInit(Queue* pq)
{
assert(pq);
pq->phead = pq->ptail = NULL;
pq->size = 0;
}
//销毁
void QueueDestroy(Queue* pq)
{
assert(pq);
QNode* cur = pq->phead;
while (cur)
{
QNode* next = cur->next;
free(cur);
cur = next;
}
pq->phead = pq->ptail = NULL;
pq->size = 0;
}
//入队列
void QueuePush(Queue* pq, QDataType x)
{
assert(pq);
//在队尾入,尾插
//创建新节点
QNode* newnode = (QNode*)malloc(sizeof(QNode));
if (newnode == NULL)
{
perror("malloc fail");
return;
}
newnode->val = x;
newnode->next = NULL;
//空链表
if (pq->phead==NULL)
{
pq->phead = pq->ptail = newnode;
}
else
{
pq->ptail->next = newnode;
pq->ptail = newnode;
}
pq->size++;
}
//出队列
void QueuePop(Queue* pq)
{
assert(pq);
//零个节点
assert(pq->phead);
//一个节点
if (pq->phead->next == NULL)
{
free(pq->phead);
pq->phead = pq->ptail = NULL;
}
else
{
QNode* next = pq->phead->next;
free(pq->phead);
pq->phead = next;
}
pq->size--;
}
//判空
bool QueueEmpty(Queue* pq)
{
assert(pq);
return pq->size == 0;
}
//取队头
QDataType QueueFront(Queue* pq)
{
assert(pq);
assert(pq->phead);
return pq->phead->val;
}
//取队尾
QDataType QueueBack(Queue* pq)
{
assert(pq);
assert(pq->ptail);
return pq->ptail->val;
}
//队列长度
size_t QueueLength(Queue* pq)
{
assert(pq);
return pq->size;
}
typedef struct {
Queue obj1;
Queue obj2;
} MyStack;
MyStack* myStackCreate() {
MyStack* p=(MyStack*)malloc(sizeof(MyStack));
QueueInit(&p->obj1);
QueueInit(&p->obj2);
return p;
}
void myStackPush(MyStack* obj, int x) {
//入栈在非空队列
if(QueueEmpty(&obj->obj1))
{
QueuePush(&obj->obj2,x);
}
else
{
QueuePush(&obj->obj1,x);
}
}
int myStackPop(MyStack* obj) {
Queue* EmptyQ=&obj->obj1;
Queue* NoEmptyQ=&obj->obj2;
if(!QueueEmpty(&obj->obj1))
{
EmptyQ=&obj->obj2;
NoEmptyQ=&obj->obj1;
}
while(QueueLength(NoEmptyQ)>1)
{
int front=QueueFront(NoEmptyQ);
QueuePush(EmptyQ,front);
QueuePop(NoEmptyQ);
}
int front=QueueFront(NoEmptyQ);
QueuePop(NoEmptyQ);
return front;
}
int myStackTop(MyStack* obj) {
Queue* EmptyQ=&obj->obj1;
Queue* NoEmptyQ=&obj->obj2;
if(!QueueEmpty(EmptyQ))
{
EmptyQ=&obj->obj2;
NoEmptyQ=&obj->obj1;
}
return QueueBack(NoEmptyQ);
}
bool myStackEmpty(MyStack* obj) {
return QueueEmpty(&obj->obj1)&&QueueEmpty(&obj->obj2);
}
void myStackFree(MyStack* obj) {
QueueDestroy(&obj->obj1);
QueueDestroy(&obj->obj2);
free(obj);
}
/**
* Your MyStack struct will be instantiated and called as such:
* MyStack* obj = myStackCreate();
* myStackPush(obj, x);
* int param_2 = myStackPop(obj);
* int param_3 = myStackTop(obj);
* bool param_4 = myStackEmpty(obj);
* myStackFree(obj);
*/