问题一:使用两个栈实现队列及其基本操作
思路:栈具有特点后进先出特点,队列具有先进先出的特点,两个栈实现队列,满足以下条件:
- 入数据时,始终保证栈为空
- 出数据时,取非空栈的栈顶元素
具体代码:
//初始化
void QueueByTwoStackInit(QBTS* q)
{
StackInit(&q->_s1);
StackInit(&q->_s2);
}
//是否为空
int QueueByTwoStackEmpty(QBTS* q)
{
assert(q);
return StackEmpty(&q->_s1) + StackEmpty(&q->_s2);
}
//入队列
void QueueByTwoStackPush(QBTS* q, DataType x)
{
assert(q);
StackPush(&q->_s1, x);
}
//出队列
void QueueByTwoStackPop(QBTS* q)
{
assert(q);
if (StackEmpty(&q->_s2) == 0)
{
while (StackEmpty(&q->_s1) != 0)
{
StackPush(&q->_s2, StackTop(&q->_s1));
StackPop(&q->_s1);
}
}
StackPop(&q->_s2);
}
//取队头数据
DataType QueueByTwoStackFront(QBTS* q)
{
assert(q);
if (StackEmpty(&q->_s2) == 0)
{
while (StackEmpty(&q->_s1) != 0)
{
StackPush(&q->_s2, StackTop(&q->_s1));
StackPop(&q->_s1);
}
}
return StackTop(&q->_s2);
}
//队列大小
size_t QueueByTwoStackSize(QBTS* q)
{
assert(q);
return StackSize(&q->_s1) + StackSize(&q->_s2);
}
问题2:使用两个队列实现一个栈及其基本操作
思路:队列具有先进先出的特点,实现栈的特点时应满足几个条件:
- 入数据时,除过第一次入队列,始终保证队列不为空
- 出数据时,假设队列数据总数为n,将其数据前n-1个存放至空的队列当中,剩余一个数据即为要出的数据
过程图:
具体代码:
//初始化
void StackByTwoQueueInit(StackByTwoQueue* s)
{
assert(s);
QueueInit(&s->_q1);
QueueInit(&s->_q2);
}
//入栈
void StackByTwoQueuePush(StackByTwoQueue* s, DataType x)
{
assert(s);
if (QueueEmpty(&s->_q1) != 0)
{
QueuePush(&s->_q1, x);
}
else
{
QueuePush(&s->_q2, x);
}
}
//出栈
void StackByTwoQueuePop(StackByTwoQueue* s)
{
Queue* empty = &s->_q1;
Queue* noempty = &s->_q2;
if (QueueEmpty(&s->_q2) == 0)
{
empty = &s->_q2;
noempty = &s->_q1;
}
while (QueueSize(noempty) > 1)
{
QueuePush(empty, QueueFront(noempty));
QueuePop(noempty);
}
QueuePop(noempty);
}
//栈顶元素
DataType StackByTwoQueueTop(StackByTwoQueue* s)
{
assert(s);
if (QueueEmpty(&s->_q1) != 0)
{
return QueueBack(&s->_q1);
}
else
{
return QueueBack(&s->_q2);
}
}
//栈大小
size_t StackByTwoQueueSize(StackByTwoQueue* s)
{
assert(s);
return QueueSize(&s->_q1) + QueueSize(&s->_q2);
}
//是否为空
int StackByTwoQueueEmpty(StackByTwoQueue* s)
{
assert(s);
return QueueEmpty(&s->_q1) + QueueEmpty(&s->_q2);
}