用两个队列实现栈---用两个队列实现栈

本文详细介绍了如何使用两个队列来实现一个栈的功能。在MyStack的创建、Push、Pop、栈顶元素获取、栈判空及释放销毁等操作中,通过巧妙地切换队列实现了栈的操作。同时,还展示了如何用队列来模拟栈,确保了数据的正确进出顺序。这种数据结构的设计思路展示了队列在实现栈功能时的灵活性。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

MyStack的创建

在这里插入图片描述

队列,队尾入,队头出,而栈只能尾部出。

出栈时,将不为空的队列,获取队头元素,push到为空的那个队列,然后不为空的队列pop,循环到最后一个元素pop掉。
入栈时,向不为空的队尾插入即可。

这样既能满足队列的性质,又能满足栈的性质,需要先码出队列及各项功能。

源队列的实现
在这里插入图片描述

typedef int Dat;

typedef struct QueNode
{
	struct QueNode* next;
	Dat data;
}Qn;

typedef struct QueList
{
	Qn* front;
	Qn* rear;
}QL;

typedef struct 
{
	QL q1;
	QL q2;
}MyStack;


MyStack* MystackCreate()
{
	MyStack* pst = (MyStack*)malloc(sizeof(MyStack));
	QueInit(&pst->q1);
	QueInit(&pst->q2);
	return pst;
}

MyStack的Push,POP

在这里插入图片描述

Push

void MyStackPush(MyStack* obj, int x)
{
	assert(obj);
	if (!QueueEmpty(&obj->q1))
	{
		QuePush(&obj->q1, x);
	}
	else
	{
		QuePush(&obj->q2, x);
	}
}

Pop,需确定哪一个是空的,与相交链表类似。

int MyStackPop(MyStack* obj)
{
	QL* emptyQ = &obj->q1;
	QL* unemptyQ = &obj->q2;
	while (QueueEmpty(&obj->q2))
	{
		QL* emptyQ = &obj->q2;
		QL* unemptyQ = &obj->q1;
	}
	while (QueSize(unemptyQ) > 1)
	{
		QuePush(emptyQ, QueFront(unemptyQ));
		QuePop(unemptyQ);
	}
	int pop = QueFront(unemptyQ);
	QuePop(unemptyQ);
	return pop;
}

栈顶元素,判空,释放销毁

栈顶元素

int MyStackTop(MyStack* obj)
{
	assert(obj);
	if (!QueEmpty(&obj->q1))
	{
		return QueRear(&obj->q1);
	}
	else
	{
		return QueRear(&obj->q2);
	}
}

判空

bool MyStackEmpty(MyStack* obj)
{
	assert(obj);
	return QueEmpty(&obj->q1) && QueEmpty(&obj->q2);
}

释放销毁

void myStackFree(MyStack* obj)
{
	assert(obj);
	QueDestory(&obj->q1);
	QueDestory(&obj->q2);
	free(obj);
}

用队列实现栈

在这里插入图片描述

解析

在这里插入图片描述

因此让一个负责入栈,一个负责出栈,当负责出栈的栈不为空则,一直出;否则就将入栈的数据pop给出栈…

在这里插入图片描述
在这里插入图片描述
需要先实现一个栈及各项功能

源栈代码

typedef struct Stack
{
	int* a;
	int size;
	int cap;
}ST;

一个负责入 一个负责出  负责出的为空了,就需要倒数据过来
因为 当你倒完数据过来 再从尾部插入,再出没法保持原来的顺序了
 1 2 3 4   4 3 2 pop 1  此时如果向不为空的push 5, 则 1 5 2 3 4
 
typedef struct MyQue
{
	ST pushst;
	ST popst;
}MyQueue;

My队列的创建

MyQueue* myQueueCreate()
{
	MyQueue* pq = (MyQueue*)malloc(sizeof(MyQueue));
	STInit(&pq->pushst);
	STInit(&pq->popst);
	return pq;
}

入队

void myQueuePush(MyQueue* obj, int x)
{
	assert(obj);
	STPush(&obj->pushst, x);
}

出队

int myQueuePop(MyQueue* obj)
{
	assert(obj);
	int top=  myQueuePeek(obj);
	STPop(&obj->popst);
	return top;
}

获取队列头部元素

int myQueuePeek(MyQueue* obj)
{
	assert(obj);
	if (STEmpty(&obj->popst))
	{
		while (!STEmpty(&obj->pushst))
		{
			STPush((&obj->popst), STCrest(&obj->pushst));
			STPop(&obj->pushst);
		}
	}
	//不为空,负责出栈的直接出
	return STCrest(&obj->popst);
}

队列判空

bool myQueueEmpty(MyQueue* obj)
{
	assert(obj);
	return STEmpty(&obj->pushst) && STEmpty(&obj->popst);
}

队列的销毁

void myQueueFree(MyQueue* obj)
{
	assert(obj);
	STFree(&obj->pushst);
	STFree(&obj->popst);
	free(obj);
	obj= NULL;
}

结束语句

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值