用栈实现队列(C语言实现)

之前的几章我讲解了栈和队列的基本特性和一些基本的操作方法,那么如何能利用栈来实现队列呢?
下面我来讲解下具体思路,栈的特性先进后出,队列是先进先出,如果要模拟队列的这个特性,我们就必须用到两个栈。
一个栈用来入队,一个栈用来出队。什么意思呢?就是我们把数据存放到第一个栈中,再把里面的数据全部移动到第二个栈后在出栈,就能够模拟出队列的先进先出的特性

假设我们操作1 ,2,3,4这四个数据
如果是队列的话
在这里插入图片描述
入队后再全部出队
在这里插入图片描述
数据还是1, 2 ,3 ,4.

然后用两个栈实现
在这里插入图片描述
先将数据全放到入队栈中
然后将入队栈的所有数据放到出队栈里面
在这里插入图片描述
再将其出栈
在这里插入图片描述
就达到了我们的目的。

下面开始代码实现

数据结构

#define STACKSIZE 100
typedef int DataType;
typedef struct Stack
{
	DataType* data;
	int top;		// 栈顶
	int capacity;  // 容量 
}Stack;

typedef struct 
{
    Stack pops;
    Stack pushs;
} MyQueue;

栈的实现部分就不再这里放了,之前几章有

初始化队列


MyQueue* myQueueCreate() 
{
    MyQueue* q = (MyQueue*)malloc(sizeof(MyQueue));
    StackInit(&q->pushs);
    StackInit(&q->pops);
    return q;
}

入队列

void myQueuePush(MyQueue* obj, int x) 
{
    StackPush(&obj->pushs, x);
}

直接把数据放入入队栈中

出队列

int myQueuePop(MyQueue* obj) 
{
    if(StackEmpty(&obj->pops))
    {
        while(!StackEmpty(&obj->pushs))
        {
            StackPush( &obj->pops, StackTop(&obj->pushs));
            StackPop(&obj->pushs);
        }
    }

    int ret = StackTop(&obj->pops);
    StackPop(&obj->pops);

    return ret;
}

当出队栈为空时把入队栈所有数据放入出队栈中,然后直接弹出栈顶

获取队首元素

int myQueuePeek(MyQueue* obj) 
{
    int top;
    if(StackEmpty(&obj->pops))
    {
        while(!StackEmpty(&obj->pushs))
        {
            StackPush( &obj->pops, StackTop(&obj->pushs));
            StackPop(&obj->pushs);
        }
    }

    top = StackTop(&obj->pops);

    return top;
}

与出队思路相同

判断队列是否为空


bool myQueueEmpty(MyQueue* obj) 
{
    if(StackEmpty(&obj->pops) && StackEmpty(&obj->pushs))
        return true;
    else
        return false;
}

判断两个栈是否同时为空,如果不是则队不为空

销毁队列


void myQueueFree(MyQueue* obj) 
{
    StackDestroy(&obj->pushs);
    StackDestroy(&obj->pops);
    free(obj);
}

这样我们就实现了用栈来实现队列,下一章讲解用队列实现栈
完整代码

#define STACKSIZE 100
typedef int DataType;
typedef struct Stack
{
	DataType* data;
	int top;		// 栈顶
	int capacity;  // 容量 
}Stack;

typedef struct {
    Stack pops;
    Stack pushs;
} MyQueue;

void ChackCapacity(Stack* ps)
{
	if (ps->top >= ps->capacity)
	{
		ps->capacity *= 2;
		ps->data = (DataType*)realloc(ps->data, ps->capacity * sizeof(DataType));

	}
}
void StackInit(Stack* ps)
{
	ps->data = (DataType*)malloc(STACKSIZE * sizeof(DataType));
	ps->top = 0;
	ps->capacity = STACKSIZE;
}

// 入栈 
void StackPush(Stack* ps, DataType data)
{
	ChackCapacity(ps);
	ps->data[ps->top++] = data;
}

// 出栈 
void StackPop(Stack* ps)
{
	if (0 == ps->top)
		return;
	ps->top--;
}

// 获取栈顶元素 
DataType StackTop(Stack* ps)
{
	if (0 == ps->top)
		return (DataType)0;
	return ps->data[ps->top - 1];
}

// 获取栈中有效元素个数 
int StackSize(Stack* ps)
{
	return ps->top;
}

// 检测栈是否为空,如果为空返回非零(1),如果不为空返回0 
int StackEmpty(Stack* ps)
{
	return ps->top == 0;
}

// 销毁栈 
void StackDestroy(Stack* ps)
{
	free(ps->data);
	ps->data = NULL;
	ps->top = 0;
	ps->capacity = 0;
}
MyQueue* myQueueCreate() {
    MyQueue* q = (MyQueue*)malloc(sizeof(MyQueue));
    StackInit(&q->pushs);
    StackInit(&q->pops);
    return q;
}

void myQueuePush(MyQueue* obj, int x) 
{
    StackPush(&obj->pushs, x);
}

int myQueuePop(MyQueue* obj) 
{
    if(StackEmpty(&obj->pops))
    {
        while(!StackEmpty(&obj->pushs))
        {
            StackPush( &obj->pops, StackTop(&obj->pushs));
            StackPop(&obj->pushs);
        }
    }

    int ret = StackTop(&obj->pops);
    StackPop(&obj->pops);

    return ret;
}

/** Get the front element. */
int myQueuePeek(MyQueue* obj) 
{
    int top;
    if(StackEmpty(&obj->pops))
    {
        while(!StackEmpty(&obj->pushs))
        {
            StackPush( &obj->pops, StackTop(&obj->pushs));
            StackPop(&obj->pushs);
        }
    }

    top = StackTop(&obj->pops);

    return top;
}

bool myQueueEmpty(MyQueue* obj) 
{
    if(StackEmpty(&obj->pops) && StackEmpty(&obj->pushs))
        return true;
    else
        return false;
}

void myQueueFree(MyQueue* obj) 
{
    StackDestroy(&obj->pushs);
    StackDestroy(&obj->pops);
    free(obj);
}
发布了60 篇原创文章 · 获赞 78 · 访问量 6322

猜你喜欢

转载自blog.csdn.net/qq_35423154/article/details/104401508