stack和queue

目录

1.什么是stack

2.容器适配器

3.stack的使用

top

push

 pop

 

4.模拟实现stack


1.什么是stack

1. stack是一种容器适配器,专门用在具有后进先出操作的上下文环境中,其删除只能从容器的一端进行 元素的插入与提取操作。(后进先出)
2. stack是作为容器适配器被实现的,容器适配器即是对特定类封装作为其底层的容器,并提供一组特定 的成员函数来访问其元素,将特定类作为其底层的,元素特定容器的尾部(即栈顶)被压入和弹出。
3. stack的底层容器可以是任何标准的容器类模板或者一些其他特定的容器类,这些容器类应该支持以下
操作:
empty:判空操作
back:获取尾部元素操作
push_back:尾部插入元素操作
pop_back:尾部删除元素操作
4. 标准容器vector、deque、list均符合这些需求,默认情况下,如果没有为stack指定特定的底层容器, 默认情况下使用deque。

2.容器适配器

容器适配器(Container Adapters)是 C++ 标准库提供的一种数据结构,它们基于现有的容器类型,提供了特定的接口和功能,以便更方便地实现某些特定的数据结构和算法。容器适配器本质上是对底层容器的封装,提供了不同的数据访问方式,使它们适用于特定的用途。 

标准库中提供了三种常用的容器适配器:

stack:栈适配器,基于底层容器提供了栈数据结构的操作,如压入(push)、弹出(pop)、查看栈顶元素等。默认底层容器是 deque,但也可以使用其他支持 back() 和 push_back() 操作的容器。


queue:队列适配器,基于底层容器提供了队列数据结构的操作,如入队(push)、出队(pop)、查看队首元素等。默认底层容器是 deque,但也可以使用其他支持 back() 和 push_back() 操作的容器。


priority_queue:优先队列适配器,基于底层容器提供了优先队列数据结构的操作,支持在插入元素时根据优先级进行排序。默认底层容器是 vector,但也可以使用其他支持随机访问和插入操作的容器。

3.stack的使用

这些是C++标准库中stack类的构造函数声明。stack是一个适配器容器,它可以使用不同的底层容器来实现栈的功能。这些构造函数声明提供了不同的方式来创建和初始化stack对象,可以根据需求选择合适的构造函数。 

stack的Construct中除了构造函数,其他什么都没有,它连拷贝构造、析构都没有。这个也跟它是容器适配器有关系,因为它的成员都是自定义类型,编译器默认生成的就够用。

stack是容器适配器以后,就开始不支持迭代器了。容器支持迭代器,容器适配器不支持迭代器。

栈随便去遍历反而是不好的,因为要保证后进先出的性质。

所以取数据得用top,想取下一个数据就得先pop。

top

reference top(); 和 const_reference top() const; 是 C++ 标准库中 std::stack 类的成员函数之一。它们用于获取栈顶元素的引用。

reference top();:返回栈顶元素的引用。如果需要修改栈顶元素,可以使用这个版本。

#include <iostream>
#include <stack>stack<int> m;m.push(42);m.push(15);// 使用 top() 获取栈顶元素int topElement = m.top();cout << "Top element: " << topElement << endl;// 修改栈顶元素m.top() = 99;cout << "New top element: " << m.top() << endl;return 0;}

 

后进先出,15先出,然后修改为99,最后出99

push

是 C++ 标准库中 std::stack 类的成员函数之一。它们用于将一个新的元素压入栈中。

这两个版本的 push 函数允许你在栈顶添加新的元素。如果需要保持传入值的不变性,可以使用第一个版本;如果你想利用移动语义来避免不必要的复制,可以使用第二个版本。
#include<iostream>
#include<stack>
using namespace std;int main() {stack<int> m;m.push(10); // 使用右值,将 10 压入栈中m.push(19);int newElement = 99;m.push(newElement); // 使用常量引用,将 newElement 压入栈中cout << "Stack size: " << m.size() << endl;while (!m.empty())  // 遍历不能用迭代器,容器适配器不支持迭代器{cout << m.top() << " "; // 输出栈顶元素m.pop(); // 弹出栈顶元素}return 0;}

 pop

void pop(); 是 C++ 标准库中 stack 类的成员函数之一。它用于将栈顶元素弹出(删除)。

这个函数没有返回值,它只是从栈中移除栈顶元素。在调用 pop() 函数之前,需要确保栈不为空,否则会导致未定义行为。

	int main() {stack<int> m;m.push(10); // 使用右值,将 10 压入栈中m.push(19);m.push(29);cout << "Stack size: " << m.size() << endl;m.pop();cout << "Stack new size: " << m.size() << endl;return 0;}

4.模拟实现stack

STL(标准模板库)中的 stack 和 queue 默认使用 std::deque 作为底层容器的原因是出于性能和功能的考虑。

std::deque(双端队列)是一个双向开口的动态数组,支持在队首和队尾进行高效的插入和删除操作。它的内部实现使得在队首和队尾的操作都能达到接近常数时间复杂度,这使得 std::deque 在作为底层容器时能够提供较好的性能
 

实现代码

#pragma once#include "string.h"
#include<iostream>
#include<stack>
#include<deque>using namespace std;namespace lty
{//适配器模式template<class T, class Container=deque<T>>class stack{public:void push(const T& x){_con.push_back(x);}void pop(){_con.pop_back();}const T& top(){return _con.back();}size_t size(){return _con.size();}bool empty(){return _con.empty();}private:Container _con;};void test_stack(){stack<int, deque<int>> st;st.push(1);st.push(2);st.push(3);st.push(4);while (!st.empty()){cout << st.top() << " ";st.pop();}cout << endl;}
}

测试代码

#include "string.h"int main()
{lty:: test_stack();
}

结果

头文件包含:代码首先包含了头文件 <deque>,这是为了使用底层容器 std::deque。

命名空间定义:代码将 stack 类放置在了命名空间 lty下,这是为了避免命名冲突和提供代码的组织结构。

stack 类模板定义:stack 类是一个模板类,有两个模板参数:T 表示栈中存储的元素类型,Container 表示底层容器的类型,默认为 std::deque<T>。

公共成员函数

push(const T& x):将传入的元素值 x 添加到底层容器的末尾,实现了入栈操作。


pop():从底层容器的末尾删除一个元素,实现了出栈操作。


T& top() 和 const T& top() const:分别返回底层容器的末尾元素的引用(允许修改)和常量引用(只读),实现了查看栈顶元素操作。


bool empty() const:返回底层容器是否为空。


size_t size() const:返回底层容器中元素的数量。


私有成员变量 _con:这是一个模板类的私有成员变量,用于存储实际的栈元素。其类型是根据模板参数 Container 确定的,在实例化时会被替换为具体的容器类型。

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

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

相关文章

C语言:一个数如果恰好等于除它本身外的因子之和,这个数就称为完数。例如6=1+2+3。编程找出1000以内的所有完数。

分析&#xff1a; 在主函数 main 中&#xff0c;程序首先定义三个整型变量 m、s 和 i&#xff0c;并用于计算和判断完数。然后使用 printf 函数输出提示信息。 接下来&#xff0c;程序使用 for 循环结构&#xff0c;从 2 到 999 遍历所有的数。对于每个遍历到的数 m&#xff0c…

如何通过nginx进行反向代理

简单介绍 正向代理 正向代理服务器是一个位于客户端和原始服务器(origin server)之间的服务器&#xff0c;为了能够从原始服务器取得内容&#xff0c;客户端向代理发送一个请求并指定目标(原始服务器)&#xff0c;然后代理向原始服务器转交请求并将获得的内容返回给客户端。正向…

Ubuntu+Tesla V100环境配置

系统基本信息 nvidia-smi’ nvidia-smi 470.182.03 driver version:470.182.03 cuda version: 11.4 查看系统体系结构 uname -aUTC 2023 x86_64 x86_64 x86_64 GNU/Linux 下载miniconda https://mirrors.tuna.tsinghua.edu.cn/anaconda/miniconda/?CM&OA https://mi…

redis报错3

INFO: Initializing SpringDispatcherServletdispatcherServlet

OpenCV快速入门:移动物体检测和目标跟踪

文章目录 前言一、移动物体检测和目标跟踪简介1.1 移动物体检测的基本概念1.2 移动物体检测算法的类型1.3 目标跟踪的基本概念1.4 目标跟踪算法的类型 二、差值法检测移动物体2.1 差值法原理2.2 差值法公式2.3 代码实现2.3.1 视频或摄像头检测移动物体2.3.2 随机动画生成的移动…

串口数据包收发的思路和流程-stm32入门

本节主要内容&#xff1a; 如何去规定一个合理的数据包格式如何收发数据包 1. 数据包格式规定/定义 1.1 HEX 数据包定义 固定包长&#xff0c;含包头包尾 可变包长&#xff0c;含包头包尾 首先数据包的作用是把一个个单独的数据给打包起来&#xff0c;方便我们进行多字节…

Java LeetCode篇-深入了解关于数组的经典解法

&#x1f525;博客主页&#xff1a; 【小扳_-CSDN博客】 ❤感谢大家点赞&#x1f44d;收藏⭐评论✍ 文章目录 1.0 轮转数组 1.1 使用移位的方式 1.2 使用三次数组逆转法 2.0 消失的数字 2.1 使用相减法 2.2 使用异或的方式 3.0 合并两个有序数组 3.1 使用三指针方式 3.2 使用合…

Spring Cache(缓存框架)

学习的最大理由是想摆脱平庸&#xff0c;早一天就多一份人生的精彩&#xff1b;迟一天就多一天平庸的困扰。各位小伙伴&#xff0c;如果您&#xff1a; 想系统/深入学习某技术知识点… 一个人摸索学习很难坚持&#xff0c;想组团高效学习… 想写博客但无从下手&#xff0c;急需…

vue 中 js 金额数字转中文

参考&#xff1a;js工具函数之数字转为中文数字和大写金额_js封装工具类函数金额大写-CSDN博客 我使用的框架vol.core。 客户需求要将录入框的金额数字转换成中文在旁边显示&#xff0c;换了几种函数&#xff0c;最终确定如下函数 function changeToChineseMoney(Num) {//判断…

Android Termux SFTP如何实现远程文件传输

文章目录 1. 安装openSSH2. 安装cpolar3. 远程SFTP连接配置4. 远程SFTP访问4. 配置固定远程连接地址 SFTP&#xff08;SSH File Transfer Protocol&#xff09;是一种基于SSH&#xff08;Secure Shell&#xff09;安全协议的文件传输协议。与FTP协议相比&#xff0c;SFTP使用了…

【24届校招】c++选手还有机会吗?如何选择更好的出路?

一、今年为什么c选手就业形势如此艰难&#xff1f; 去年c岗位的火热&#xff0c;不少c选手拿到高薪offer&#xff0c;今年转c的人群变多&#xff0c;内卷加剧&#xff0c;高学历大佬多如牛毛&#xff0c;很多比较好的c岗位多人投递&#xff0c;僧多肉少。 从行情来说&#xf…

Selenium-Unittest单元测试框架

1、Unittest介绍 为什么要学习单元测试框架 测试用例的组织与运行需要单元测试框架的参与&#xff0c;从而满足不同测试场景的需要&#xff0c;单元测试框架提供了丰富的比较方法&#xff1a;实际结果与预期结果的对比测试结果 单元测试框架提供了丰富的日志&#xff1a;给出测…

livox 半固体激光雷达 gazebo 仿真 | 安装与验证

livox 半固体激光雷达 gazebo 仿真 | 安装与验证 livox 半固体激光雷达 gazebo 仿真 | 安装与验证livox 介绍安装验证 livox 半固体激光雷达 gazebo 仿真 | 安装与验证 livox 介绍 览沃科技有限公司&#xff08;Livox&#xff09;成立于2016年。为了革新激光雷达行业&#xf…

web:[NPUCTF2020]ReadlezPHP

题目 打开页面显示如下 没发现其他的线索&#xff0c;查看源代码 发现一个网址&#xff0c;访问这个页面查看 进行代码审计 这段代码是一个简单的 PHP 类&#xff0c;名为 HelloPhp。它有两个公共属性 $a 和 $b&#xff0c;并在构造函数中将它们分别初始化为字符串 "Y-m-…

Java 设计模式之命令模式

命令模式 介绍 命令模式是一种行为类设计模式&#xff0c;核心是将每种请求或操作封装为一个独立的对象&#xff0c;从而可以集中管理这些请求或操作&#xff0c;比如将请求队列化依次执行、或者对操作进行记录和撤销。 命令模式通过将请求的发送者&#xff08;客户端&#x…

Failed to load resource: the server responded with a status of 404 ()

路径问题&#xff1a; 路径省略前面的http://localhost:8080/ 就行了。

中兴交换机:DHCP的配置

一、配置说明 拓扑图 S1是中兴三层核心交换机&#xff0c;作为DHCP Server使用&#xff0c;同时作为网关&#xff0c;PC通过自动获取IP地址接入网络 注意事项&#xff1a; S1全局下需要配置&#xff1a;IP Pool&#xff0c;DHCP Policy&#xff0c;打开DHCP功能 S1接口下需…

Springboot实现增删改差

一、包结构 二、各层代码 (1)数据User public class User {private Integer id;private String userName;private String note;public User() {super();}public User(Integer i, String userName, String note) {super();this.id i;this.userName userName;this.note note;…

2.前端--HTML标签基本概念【2023.11.25】

1.基本语法规范 HTML 标签是由尖括号包围的关键词&#xff0c;例如 <html>。HTML 标签通常是成对出现的&#xff0c;例如 和 &#xff0c;我们称为双标签。有些特殊的标签必须是单个标签&#xff08;极少情况&#xff09;&#xff0c;例如 <br />我们称为单标签。 …

深度学习之基于YoloV3杂草识别系统

欢迎大家点赞、收藏、关注、评论啦 &#xff0c;由于篇幅有限&#xff0c;只展示了部分核心代码。 文章目录 一项目简介 二、功能三、系统四. 总结 一项目简介 深度学习在图像识别领域已经取得了显著的成果&#xff0c;其中基于YOLO&#xff08;You Only Look Once&#xff09…