【力扣+C语言】225.用队列实现栈


目录

1.力扣 225.用队列实现栈

1.1.题目

1.2.题目分析

1.2.1.题目思路分析:

1.2.2.准备过程:创建结构体+实现函数myStackCreate

 1.2.3实现push函数,将元素 x 压入栈顶。

1.2.4.实现pop函数:移除并返回栈顶元素

1.2.5实现top函数: 返回栈顶元素

1.2.6.实现empty函数:判断栈是否为空 

1.2.7实现free函数,释放空间

1.3.题目答案

最后


推荐阅读顺序:

1.题目->3.答案->2.题目分析->4.题目知识点


1.力扣 225.用队列实现栈

225. 用队列实现栈 - 力扣(LeetCode)https://leetcode.cn/problems/implement-stack-using-queues/


1.1.题目

请你仅使用两个队列实现一个后入先出(LIFO)的栈,并支持普通栈的全部四种操作(push、top、pop 和 empty)。

实现 MyStack 类:

void push(int x) 将元素 x 压入栈顶。
int pop() 移除并返回栈顶元素。
int top() 返回栈顶元素。
boolean empty() 如果栈是空的,返回 true ;否则,返回 false 。
 

注意:

你只能使用队列的基本操作 —— 也就是 push to back、peek/pop from front、size 和 is empty 这些操作。
你所使用的语言也许不支持队列。 你可以使用 list (列表)或者 deque(双端队列)来模拟一个队列 , 只要是标准的队列操作即可。


1.2.题目分析

由于C语言中没有对应的队列函数可以使用,就需要我们自己手动实现队列。详情可移步我的这篇博文:

(6条消息) 【数据结构】队列、环形队列_vpurple__的博客-CSDN博客https://blog.csdn.net/vpurple_/article/details/126200057?spm=1001.2014.3001.5501


1.2.1.题目思路分析:

栈和队列特点对比:

栈:后进先出

队列:先进先出

在使用两个队列模拟栈时,可以采用始终保持一个栈为空的思路,在进数据的时候就只往非空的那个队列进数据,在出数据的时候就把两个队列中的内容倒一下。本题目共需要实现4个主体函数:

分别为:

void push(int x) 将元素 x 压入栈顶。
int pop() 移除并返回栈顶元素。
int top() 返回栈顶元素。
boolean empty() 如果栈是空的,返回 true ;否则,返回 false 。


1.2.2.准备过程:创建结构体+实现函数myStackCreate

根据之前队列的定义,在MyStack中定义两个队列:

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

实现myStackCreate函数:

易错点:

野指针问题

 正确写法:


 1.2.3实现push函数,将元素 x 压入栈顶。


1.2.4.实现pop函数:移除并返回栈顶元素


1.2.5实现top函数: 返回栈顶元素


1.2.6.实现empty函数:判断栈是否为空 

1.2.7实现free函数,释放空间


1.3.题目答案

typedef int  QDataType;

//用单链表实现队列

// 链式结构:表示队列 
typedef struct QListNode
{
	struct QListNode* next;
	QDataType data;
}QNode;

// 队列的结构 
typedef struct Queue
{
	QNode* front;
	QNode* rear;
}Queue;


// 初始化队列 
void QueueInit(Queue* q)
{
	assert(q);
	q->front =q->rear= NULL;
}


// 检测队列是否为空,如果为空返回非零结果,如果非空返回0 

bool QueueEmpty(Queue* q)
{
	assert(q);
	return q->front == NULL&&q->rear==NULL;
}


QNode* AddNode(QDataType data)
{
	QNode* p = (QNode*)malloc(sizeof(QNode));
	if (p == NULL)
	{
		perror("malloc error\n");
		exit(-1);
	}
	p->data = data;
	//队列申请新节点next要置为空
	p->next = NULL;
	return p;
}
//从队尾添加数据
// 队尾入队列 
void QueuePush(Queue* q, QDataType data)
{
	assert(q);
	if (q->front == NULL)
	{
		q->front = q->rear = AddNode(data);
	}
	else
	{
		QNode* tail = AddNode(data);
		q->rear->next = tail;
		q->rear = tail;
		q->rear->next = NULL;
	}

}

// 队头出队列 
void QueuePop(Queue* q)
{
	assert(q);
	assert(q->front);

	//如果删除的是最后一个
	if (q->front->next == NULL)
	{
		free(q->front);
		q->front = q->rear = NULL;
	}

	QNode* head = q->front;
    //
    //
    if(q->front!=NULL)
    {
        q->front = q->front->next;
    }

	free(head);
	head = NULL;

}

// 获取队列头部元素 
QDataType QueueFront(Queue* q)
{
	assert(q);
    assert( !QueueEmpty(q));

	return q->front->data;
}

// 获取队列队尾元素 

QDataType QueueBack(Queue* q)
{
	assert(q);
	assert(!QueueEmpty(q));
  
	return q->rear->data;
}


// 获取队列中有效元素个数 
int QueueSize(Queue* q)
{
	assert(q);
	int i = 0;
	QNode* head = q->front;

	while (head)
	{
		i++;
		head = head->next;
	}
	return i;
}

// 销毁队列 
void QueueDestroy(Queue* q)
{
	assert(q);
	assert(QueueEmpty);
	QNode* head = q->front;
	QNode* next = NULL;
	while (head)
	{
		next = head->next;
		free(head);
		head=next;
	}
	q->front = q->rear = NULL;//销毁队列之后记得把头尾指针置为空
}


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


MyStack* myStackCreate() {
    MyStack* St=(MyStack*)malloc(sizeof(MyStack));
    QueueInit(&St->q1);
    QueueInit(&St->q2);
    return St;
}

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

int myStackPop(MyStack* obj) {
    Queue* empty=&obj->q1;
    Queue* unempty=&obj->q2;
    if( !QueueEmpty(&obj->q1))
    {
       empty=&obj->q2;
      unempty=&obj->q1;
    }
    while(QueueSize(unempty)>1)
    {
        QueuePush(empty,QueueFront(unempty));
        QueuePop(unempty);
    }
    int pop=QueueFront(unempty);
    QueuePop(unempty);
    return pop;
}

int myStackTop(MyStack* obj) {
    Queue* empty=&obj->q1;
    Queue* unempty=&obj->q2;
    if( !QueueEmpty(&obj->q1))
    {
        empty=&obj->q2;
        unempty=&obj->q1;
    }
    return QueueBack(unempty);
}

bool myStackEmpty(MyStack* obj) {
    if(QueueEmpty(&obj->q1)&&QueueEmpty(&obj->q2))
    {
        return true;
    }
    return false;
}

void myStackFree(MyStack* obj) {
    QueueDestroy(&obj->q1);
    QueueDestroy(&obj->q2);
    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);
*/

最后

大家好这里是媛仔!希望这篇解答对你可以有所帮助,和小狗狗一起祝你天天开心哦~

  • 27
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 56
    评论
请问您需要的是两个数组的交集元素还是交集元素的数量? 如果是交集元素,可以采用双指针的方式,先将两个数组排序,然后设定两个指针 i 和 j,分别指向两个数组的开头,比较两个指针所指向的元素的大小,如果相等,则说明找到了一个交集元素,将其存到结果数组中;如果不相等,则将指向小的元素的指针向后移动一位,直到其中一个指针越界为止。 代码实现如下: ```c int* intersect(int* nums1, int nums1Size, int* nums2, int nums2Size, int* returnSize){ int i = 0, j = 0, k = 0; int* res = (int*)malloc(sizeof(int) * (nums1Size > nums2Size ? nums2Size : nums1Size)); // 排序 qsort(nums1, nums1Size, sizeof(int), cmp); qsort(nums2, nums2Size, sizeof(int), cmp); while (i < nums1Size && j < nums2Size) { if (nums1[i] == nums2[j]) { res[k++] = nums1[i]; i++; j++; } else if (nums1[i] < nums2[j]) { i++; } else { j++; } } *returnSize = k; return res; } int cmp(const void* a, const void* b) { return *(int*)a - *(int*)b; } ``` 如果是交集元素的数量,可以采用哈希表的方式,用一个哈希表来记录第一个数组中的元素出现的次数,然后遍历第二个数组,在哈希表中查找是否存在相同的元素,如果存在,则说明找到了一个交集元素,将其计数并从哈希表中删除该元素,最后返回计数结果即可。 代码实现如下: ```c int* intersect(int* nums1, int nums1Size, int* nums2, int nums2Size, int* returnSize){ int i = 0, j = 0, k = 0; int* res = (int*)malloc(sizeof(int) * (nums1Size > nums2Size ? nums2Size : nums1Size)); int* hash = (int*)malloc(sizeof(int) * 1001); // 由于题目条件限制在 [0, 1000] 范围内,所以哈希表可以开得比较小 memset(hash, 0, sizeof(hash)); for (i = 0; i < nums1Size; i++) { hash[nums1[i]]++; } for (j = 0; j < nums2Size; j++) { if (hash[nums2[j]] > 0) { res[k++] = nums2[j]; hash[nums2[j]]--; } } *returnSize = k; return res; } ``` 希望这些代码能够帮到您,如有疑问请随时问我~
评论 56
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

vpurple__

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值