【基础数据结构】栈和队列

例题1

化栈为队

实现一个MyQueue类,该类用两个栈来实现一个队列。

示例:

MyQueue queue = new MyQueue();
queue.push(1);
queue.push(2);
queue.peek();  // 返回 1
queue.pop();   // 返回 1
queue.empty(); // 返回 false

说明:

  • 你只能使用标准的栈操作 -- 也就是只有 push to toppeek/pop from topsize 和 is empty 操作是合法的。
  • 你所使用的语言也许不支持栈。你可以使用 list 或者 deque(双端队列)来模拟一个栈,只要是标准的栈操作即可。
  • 假设所有操作都是有效的 (例如,一个空的队列不会调用 pop 或者 peek 操作)。

(C语言)

这段代码实现了使用两个栈来模拟队列的功能。栈是一种后进先出(LIFO)的数据结构,而队列是一种先进先出(FIFO)的数据结构。通过使用两个栈,我们可以达到模拟队列的效果。

整体的思路如下:

1. 首先,我们定义了一个结构体 `MyQueue`,它包含一个数组 `elements` 用于存储队列元素,以及 `front` 和 `rear` 分别表示队列的前端和后端。

2. 初始化队列时,我们将 `front` 和 `rear` 的初始值都设为 -1,表示队列为空。

3. 入队操作 `push`:

  •     首先检查队列是否已满,如果后端指针 `rear` 已经指向数组的最后一个位置(`MAX_SIZE - 1`),则队列已满,无法再插入元素。
  •     如果队列不满,我们将要插入的元素放入数组的后端,并将 `rear` 后移一位。
  •     如果队列之前为空(即 `front` 为初始值 -1),则将 `front` 移动到数组的第一个元素。

4. 出队操作 `pop`:

  •     首先检查队列是否为空,如果前端指针 `front` 为初始值 -1 或者 `front` 大于 `rear`,则队列为空,无法进行出队操作。
  •     如果队列不为空,我们返回数组前端指针 `front` 所指向的元素,并将 `front` 后移一位。

5. 查看队头元素操作 `peek`:

  •     首先检查队列是否为空,如果前端指针 `front` 为初始值 -1 或者 `front` 大于 `rear`,则队列为空,无法获取队头元素。
  •     如果队列不为空,我们返回数组前端指针 `front` 所指向的元素,但不改变 `front` 的位置。

6. 判断队列是否为空操作 `isEmpty`:

  •     如果前端指针 `front` 为初始值 -1 或者 `front` 大于 `rear`,则队列为空,返回 `true`,否则返回 `false`。

在 `main` 函数中,我们使用上述操作函数来对模拟队列进行一些简单的测试:

  •  首先,我们创建一个 `MyQueue` 对象 `queue` 并初始化。
  •  然后,我们调用 `push` 函数两次将元素 1 和 2 入队,依次变为 [1, 2]。
  •  接下来,我们调用 `peek` 函数获取队头元素,即 1,并打印出来。
  •  然后,我们调用 `pop` 函数将队头元素 1 出队,并打印出来。
  •  最后,我们调用 `isEmpty` 函数判断队列是否为空,并将结果打印出来。

这样,我们就完成了使用两个栈来模拟队列的功能。

C++

#include <stack>
#include<iostream>
class MyQueue {
private:std::stack<int> inStack;  // 用于入队的栈std::stack<int> outStack; // 用于出队的栈public:MyQueue() {}void push(int x) {inStack.push(x);  // 将元素压入入队栈}int pop() {if (outStack.empty()) {// 如果出队栈为空,将入队栈中的元素依次弹出并压入出队栈while (!inStack.empty()) {outStack.push(inStack.top());inStack.pop();}}int front = outStack.top(); // 获取队头元素outStack.pop();             // 弹出队头元素return front;}int peek() {if (outStack.empty()) {// 如果出队栈为空,将入队栈中的元素依次弹出并压入出队栈while (!inStack.empty()) {outStack.push(inStack.top());inStack.pop();}}return outStack.top();  // 返回队头元素}bool empty() {return inStack.empty() && outStack.empty();  // 判断队列是否为空}
};int main() {MyQueue queue;queue.push(1);queue.push(2);int peekValue = queue.peek(); // 返回 1int popValue = queue.pop();   // 返回 1bool isEmpty = queue.empty(); // 返回 falsestd::cout << peekValue << " " << popValue << " ";if(isEmpty){std::cout<<"空";}else{std::cout<<"非空";}return 0;
}

C

#include <stdio.h>
#include <stdlib.h>#define MAX_SIZE 100typedef struct {int elements[MAX_SIZE];int front;int rear;
} MyQueue;void initQueue(MyQueue* queue) {queue->front = -1;  // 初始化队列的前端指针为-1queue->rear = -1;   // 初始化队列的后端指针为-1
}void push(MyQueue* queue, int x) {if (queue->rear == MAX_SIZE - 1) {printf("Queue is full. Cannot push element.\n");return;  // 如果队列已满,则无法将元素入队,直接返回}queue->elements[++queue->rear] = x;  // 将元素x入队到队尾if (queue->front == -1) {queue->front = 0;  // 如果队列为空,将前端指针指向队列的第一个元素}
}int pop(MyQueue* queue) {if (queue->front == -1 || queue->front > queue->rear) {printf("Queue is empty. Cannot pop element.\n");return -1;  // 如果队列为空或前端指针大于后端指针,则无法将元素出队,直接返回-1}return queue->elements[queue->front++];  // 将前端指针指向的元素出队,并将前端指针后移
}int peek(MyQueue* queue) {if (queue->front == -1 || queue->front > queue->rear) {printf("Queue is empty. Cannot peek element.\n");return -1;  // 如果队列为空或前端指针大于后端指针,则无法获取队头元素,直接返回-1}return queue->elements[queue->front];  // 返回前端指针指向的元素,不改变前端指针的位置
}int isEmpty(MyQueue* queue) {return (queue->front == -1 || queue->front > queue->rear);  // 判断队列是否为空,如果前端指针大于后端指针,则为空
}int main() {MyQueue queue;initQueue(&queue);  // 初始化队列push(&queue, 1);  // 入队元素1push(&queue, 2);  // 入队元素2int peekValue = peek(&queue);  // 获取队头元素printf("Peek: %d\n", peekValue);  // 打印队头元素int popValue = pop(&queue);  // 出队元素printf("Pop: %d\n", popValue);  // 打印出队元素int empty = isEmpty(&queue);  // 判断队列是否为空printf("Is empty: %s\n", empty ? "true" : "false");  // 打印队列是否为空的结果return 0;
}

例题2

用队列实现栈

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

实现 MyStack 类:

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

注意:

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

示例:

输入:
["MyStack", "push", "push", "top", "pop", "empty"]
[[], [1], [2], [], [], []]
输出:
[null, null, null, 2, 2, false]
解释:
MyStack myStack = new MyStack();
myStack.push(1);
myStack.push(2);
myStack.top(); // 返回 2
myStack.pop(); // 返回 2
myStack.empty(); // 返回 False

提示:

  • 1 <= x <= 9
  • 最多调用100 次 pushpoptop 和 empty
  • 每次调用 pop 和 top 都保证栈不为空

(C语言)

题目要求使用两个队列实现一个后入先出(LIFO)的栈,并支持栈的常见操作:push、pop、top和empty。

我们可以借助两个队列来模拟栈的行为。其中一个队列作为主队列,用于存储栈的元素,另一个队列作为辅助队列,在执行出栈操作时辅助完成元素的移动。

具体的做题思路如下:

1. 定义一个类 `MyStack`,并声明两个队列,一个用于存储栈的元素,命名为 `mainQueue`,另一个作为辅助队列,命名为 `helperQueue`。

2. 实现 `push` 操作:

  •    将元素 `x` 推入 `mainQueue` 中即可。

3. 实现 `pop` 操作:

  •    将 `mainQueue` 中的元素移动到 `helperQueue` 中,直到 `mainQueue` 中只剩下一个元素为止。
  •    弹出 `mainQueue` 中的最后一个元素并返回。
  •    将 `helperQueue` 重新赋值给 `mainQueue`。

4. 实现 `top` 操作:

  •    将 `mainQueue` 中的元素移动到 `helperQueue` 中,直到 `mainQueue` 中只剩下一个元素为止。
  •    获取 `mainQueue` 中的最后一个元素并返回。
  •    将 `helperQueue` 重新赋值给 `mainQueue`。

5. 实现 `empty` 操作:

  •    当且仅当 `mainQueue` 为空时,栈为空,返回 `true`,否则返回 `false`。

通过以上操作,我们可以使用两个队列模拟一个后入先出的栈。具体实现时,出栈和获取栈顶元素时,需要将元素从一个队列移动到另一个队列,以保持栈的后入先出的特性。

C 

#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>typedef struct {int* data;  // 存储栈元素的数组int top;    // 栈顶指针int maxSize; // 栈的最大容量
} MyStack;/** Initialize your data structure here. */
MyStack* myStackCreate(int maxSize) {MyStack* stack = (MyStack*)malloc(sizeof(MyStack));stack->data = (int*)malloc(sizeof(int) * maxSize);stack->top = -1;        // 初始化栈顶指针为-1stack->maxSize = maxSize;return stack;
}/** Push element x onto stack. */
void myStackPush(MyStack* obj, int x) {obj->top++;                     // 栈顶指针加1obj->data[obj->top] = x;         // 将元素x存入栈顶位置
}/** Removes the element on top of the stack and returns that element. */
int myStackPop(MyStack* obj) {int topElement = obj->data[obj->top];   // 获取栈顶元素obj->top--;                            // 栈顶指针减1return topElement;
}/** Get the top element. */
int myStackTop(MyStack* obj) {return obj->data[obj->top];     // 返回栈顶元素
}/** Returns whether the stack is empty. */
bool myStackEmpty(MyStack* obj) {return (obj->top == -1);       // 栈空的条件是栈顶指针为-1
}/** Free memory allocated to the stack. */
void myStackFree(MyStack* obj) {free(obj->data);    // 释放存储栈元素的数组内存free(obj);          // 释放栈结构体内存
}int main() {MyStack* stack = myStackCreate(5);   // 创建容量为5的栈myStackPush(stack, 1);              // 入栈操作myStackPush(stack, 2);myStackPush(stack, 3);printf("%d\n", myStackTop(stack));  // 获取栈顶元素printf("%d\n", myStackPop(stack));  // 出栈操作printf("%s\n", myStackEmpty(stack) ? "true" : "false");  // 判断栈是否为空myStackFree(stack);                  // 释放栈内存return 0;
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/618465.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Linux QT以太网配置及相关知识

Linux QT以太网配置及相关知识 平台和内容概述安装Qt Creator设计用户界面编辑源代码自定义LineEdit创建槽函数以太网逻辑功能实现静态配置ui逻辑:功能概述代码实现DNS退出程序输入框中的ip规范保存数据和读取数据构建文件编译运行平台注意点开机自动配置以太网总结平台和内容…

FreeRtos Queue (一)

本篇主要讲队列的数据结构和初始化 一、队列的数据结构 二、队列初始化完是什么样子的 队列初始化的函数调用关系&#xff1a;xQueueGenericCreate->prvInitialiseNewQueue->xQueueGenericReset 所以&#xff0c;最终初始化完的队列是这样的 假设申请了4个消息体&…

SQL:一行中存在任一指标就显示出来

当想要统计的两个指标不在一张表中时&#xff0c;需要做关联。但很多情况下&#xff0c;也没有办法保证其中一张表的维度是全的&#xff0c;用left join或right join可能会导致数据丢失。所以借助full join处理。 如&#xff0c;将下面的数据处理成表格中的效果&#xff08;维…

天下没有免费的午餐:AI技术进步与代价辩证分析

“天下没有免费的午餐”这一经济学原理揭示了在资源有限的世界中&#xff0c;任何收益或优势都必然伴随着相应的成本和牺牲。当我们将这一观点引入人工智能领域时&#xff0c;我们可以深入探讨AI技术的进步与发展所带来的巨大变革背后所隐藏的成本、挑战以及伦理道德问题。 一、…

AI副业拆解:人像卡通化,赋予你的形象全新生命力

大家好我是在看&#xff0c;记录普通人学习探索AI之路。 &#x1f525;让你的形象瞬间穿越二次元&#xff01;&#x1f680;人像卡通化&#xff0c;捕捉你的独特魅力&#xff0c;让真实与梦幻在此刻交融。&#x1f3a8; 今天为大家介绍如何免费把人像卡通化--漫画风 https://w…

【征稿进行时|见刊、检索快速稳定】2024年经济发展与旅游管理国际学术会议(ICEDTM 2024)

【征稿进行时|见刊、检索快速稳定】2024年经济发展与旅游管理国际学术会议(ICEDTM 2024) 2024 International Conference Economic Development and Tourism Management(ICEDTM 2024) 一、【会议简介】 ICEDTM 2024将围绕"旅游管理”“经济发展”的最新研究领域&#xff…

大模型开启应用时代 数钉科技一锤定音

叮叮叮叮&#xff01;数钉智造大模型&#xff0c;“定音”强势发布&#xff01; 随着科技的飞速发展&#xff0c;大模型技术已逐渐成为推动产业变革的核心力量。在这一浪潮中&#xff0c;数钉科技凭借深厚的技术积累和敏锐的市场洞察力&#xff0c;成功利用大模型技术搭建起智能…

<蓝桥杯软件赛>零基础备赛20周--第13周--DFS剪枝

报名明年4月蓝桥杯软件赛的同学们&#xff0c;如果你是大一零基础&#xff0c;目前懵懂中&#xff0c;不知该怎么办&#xff0c;可以看看本博客系列&#xff1a;备赛20周合集 20周的完整安排请点击&#xff1a;20周计划 每周发1个博客&#xff0c;共20周。 在QQ群上答疑&#x…

在ubuntu上的18个非常实用的命令行工具软件

使用Ubuntu的过程中&#xff0c;在终端上使用命令行工具是非常常见的事情&#xff0c;熟练地掌握命令行工具是使用ubuntu必不可少的技能&#xff0c;即便是Ubuntu的初学者&#xff0c;通常也很熟悉诸如ls、rm、cp等一些文件操作工具&#xff0c;当浏览/bin目录时&#xff0c;你…

Shell编程自动化之if、for、while和函数

一、if语句 1.单分支格式 if [ 条件判断式 ]; then当条件判断成立时&#xff0c;执行的命令内容 fi if [ 条件判断式 ] then当条件判断成立时&#xff0c;执行的命令内容 fi 2.双分支格式 if [ 条件判断式 ]; then当条件判断成立时&#xff0c;执行的命令内…

【CCNet】《CCNet:Criss-Cross Attention for Semantic Segmentation》

ICCV-2019 文章目录 1 Background and Motivation2 Related Work3 Advantages / Contributions4 Method5 Experiments5.1 Datasets and Metrics5.2 Experiments on Cityscapess5.3 Experiments on ADE20K5.4 Experiments on COCO 6 Conclusion&#xff08;own&#xff09; 1 Ba…

MAC通过终端,使用python3建立本地Web服务

实现局域网Web服务&#xff0c;很简单几句命令&#xff0c;一起看看。 1. 我相信你已经有 brew(Homebrew 包管理器) 了对么? 如果没有可以执行这个方法 /bin/bash -c "$(curl -fsSL https://raw.githubusercontent.com/Homebrew/install/HEAD/install.sh)"2. 安…

网页的介绍

目录 什么是网页&#xff1a; 网页的组成&#xff1a; 什么是HTML&#xff1a; 网页的总结&#xff1a; 浏览器&#xff1a; web标准&#xff1a; 为什么需要Web标准&#xff1a; web标准的构成&#xff1a; 什么是网页&#xff1a; 1.网站是指在因特网上根据一定的规…

openal中使用现代C++智能指针管理ffmpeg中裸指针的用法

裸指针包装 /* Define unique_ptrs to auto-cleanup associated ffmpeg objects. */ struct AVIOContextDeleter {void operator()(AVIOContext *ptr) { avio_closep(&ptr); } }; using AVIOContextPtr std::unique_ptr<AVIOContext,AVIOContextDeleter>;struct AVF…

清晰讲解Cookie、Session、Token、JWT之间的区别

文章目录 什么是认证(Authentication)什么是授权(Authorization)什么是凭证(Credentials)什么是Cookie什么是SessionSession的痛点 Cookie 和 Session 的区别什么是Token(令牌)Acesss TokenRefresh Token Token 和 Session 的区别Token 与 Cookie什么是 JWT生成JWTJWT 的原理JW…

利用PowerShell和Mkvtoolnix批量去除视频封面

利用PowerShell v5和Mkvtoolnix批量去除视频封面 PowerShell Version : 5.1.22621.2506 foreach ($file in Get-ChildItem "*.mp4") { Start-Process -FilePath "C:\Program Files\MKVToolNix\mkvmerge.exe" -ArgumentList "--ui-language en --pr…

Memcache简介与运维

开源、高性能、高并发的分布式内存缓存系统。 作用 缓存关系型数据库的结果&#xff0c;减少数据库自身访问的次数。 常见内存缓存服务软件对比 memcache 纯内存 redis、memcachedb 可持久化存储&#xff0c;同时会使用磁盘存 …

idea使用docker-compose发布应用程序

非常重要的话说在前头 idea要想使用docker-compose&#xff0c;不能使用ssh创建idea Docker&#xff0c;而需要使用socket创建idea Docker。 socket docker是不安全的&#xff0c;任何人都可以访问你的docker&#xff0c;所以只能测试环境使用&#xff0c;请勿在正式环境使用s…

问题解决记录-pypcd

项目场景&#xff1a; python3 环境下使用 pypcd 读取点云 pcd 文件 pip install pypcd 安装 pypcd 库 问题描述 读取pcd 文件时候报错 问题 1、 import cStringIO as sio ModuleNotFoundError: No module named cStringIOpython3.X已经取消了cStringIO模块 网上建议&…

UniApp 面试题

UniApp 面试题 1. 什么是 UniApp&#xff1f;它有什么特点&#xff1f; 答案&#xff1a;UniApp 是一个基于 Vue.js 的跨平台应用开发框架&#xff0c;可以使用 Vue.js 的开发语法编写一次代码&#xff0c;然后通过编译生成可以在多个平台&#xff08;包括iOS、Android、H5 等…