当前位置: 首页 > news >正文

C++轮子 · STL 序列容器

STL中大家最耳熟能详的可能就是容器,容器大致可以分为两类,序列型容器(SequenceContainer)和关联型容器(AssociativeContainer)这篇文章中将会重点介绍STL中的各种序列型容器和相关的容器适配器。主要内容包括

  • std::vector
  • std::array
  • std::deque
  • std::queue
  • std::stack
  • std::priority_queue
  • std::list
  • std::forward_list

std::vector

提到STL,大部分人的第一反应是容器,而提到容器大部分人首先想到的是std::vector。斯特劳斯特卢普的观点来说,std::vector是所有的容器中的首先,如果你不清楚应该使用哪个容器,那就选std::vector吧(当然,你不应该不清楚选哪个容器,合格是程序员对自己写的代码应该要了如指掌)。

std::vector的使用非常简单,下面是一个简单的例子。

#include <vector>                               // 1int main(int argc, char* argv[]) {std::vector<int> ages = { 1, 2, 3, 4 };     // 2return 0;
}

头文件

// 1中引入了std::vector的头文件,需要注意的是所有C++标准库的头文件都是没有.h结尾的。这么做是为了区分,C标准库的头文件和C++标准库的头文件。比如最具代表性的:

#include <string.h>     // C 标准库头文件,包含 strlen,memset 等函数
#include <string>       // C++ 标准库头文件,包含 std::string 类

此外对于所有C标准库头文件,如果你是在C++项目中引用,你应该使用#include <cxxx>这种方式而不是#include <xxx.h>这种形式。也就是说我们应该使用#include <cstring>而不是#include <string.h>

std::vector 还是 vector

我见过很多的人(包括很多书)的习惯是在源文件头部写上using namespace std;然后在代码中使用vector<int>,而不是直接使用std::vector<int>

我个人的习惯是直接使用std::vector<int>,因为namespace对我来说是一个模块,写明了std::有更强的模块内聚表达力,而且也不太容易出现名字碰撞。

初始化

// 2在构造std::vector的时候直接给了初始值,这是C++11的特性,在C++11之前不能这样写,有一种大致等同的写法如下:

int initilizer[4] = { 1, 2, 3, 4 };
std::vector<int> ages(initilizer, initilizer + 4);

std::vector<int> ages = { 1, 2, 3, 4 }这种写法实际上从语法分析上来说是分成下面几个步骤的:

  1. { 1, 2, 3, 4 } 被编译器构造成一个临时变量std::initializer_list<int>,然后使用临时变量构造一个临时变量 std::vector<int>,然后再用 std::vector<int>的拷贝构造函数构造最终的ages
std::initializer_list<int> initilizer;
std::vector<int> tmp(initilizer);
std::vector<int> ags(tmp);

当然上面的分析只是语法上的分析,绝大部分编译器都可以优化掉tmp,而且因为{1, 2, 3, 4}转换成std::initializer_list是编译器在编译器完成的事情,所以其实效率比我们想象中要高一些。

std::vector

std::vector有一个特化版本std::vector<bool>,用于实现dynamic bitset,需要注意的是,这个特化版本并不是容器,它的迭代器无法很好的适配STL中的所有算法。它的存在是为了节省空间,它的每一个元素只占用一位而不是一个字节。为了实现这种优化,operator[]返回的是一个代理类,你没有办法取单个元素的地址。通常的建议是,如果你不需要动态的bitset,你可以使用std::bitset,如果你需要dynamic bitset你可以考虑使用std::deque<bool>替代。

push_back vs emplace_back

C++11在容器尾部添加一个元素调用的函数是push_back,它在libcxx中的实现如下:

template <class _Tp, class _Allocator>
inline _LIBCPP_INLINE_VISIBILITY
void
vector<_Tp, _Allocator>::push_back(const_reference __x)
{if (this->__end_ != this->__end_cap()){__RAII_IncreaseAnnotator __annotator(*this);__alloc_traits::construct(this->__alloc(),_VSTD::__to_raw_pointer(this->__end_), __x);__annotator.__done();++this->__end_;}else__push_back_slow_path(__x);
}

这里存在两次元素的构造,一次是 __x 参数的构造,一次是容器内部原始的拷贝构造。也就是说使用拷贝构造在末尾构造一个新的元素。emplace_back是C++11为减少其中一次拷贝而引入的新的接口,在libcxx中的实现如下

template <class _Tp, class _Allocator>
template <class... _Args>
inline
#if _LIBCPP_STD_VER > 14
typename vector<_Tp, _Allocator>::reference
#else
void
#endif
vector<_Tp, _Allocator>::emplace_back(_Args&&... __args)
{if (this->__end_ < this->__end_cap()){__RAII_IncreaseAnnotator __annotator(*this);__alloc_traits::construct(this->__alloc(),_VSTD::__to_raw_pointer(this->__end_),

相关文章:

C++轮子 · STL 序列容器

STL中大家最耳熟能详的可能就是容器,容器大致可以分为两类,序列型容器(SequenceContainer)和关联型容器(AssociativeContainer)这篇文章中将会重点介绍STL中的各种序列型容器和相关的容器适配器。主要内容包括 std::vectorstd::arraystd::dequestd::queuestd::stackstd::…...

浅谈智慧路灯安全智能供电方案设计

摘要: 智慧路灯&#xff0c;作为智慧城市、新基建、城市更新的主要组成部分&#xff0c;近些年在各大城市已得到很好的落地和 应用&#xff0c;但其与传统路灯相比集成大量异元异构电子设备&#xff0c;这些设备的供电电压、接口形式、权属单位各不相同&#xff0c; 如何设计一…...

C#设计模式教程(2):工厂方法模式

工厂方法模式是一种创建型设计模式,它定义了一个用于创建对象的接口,但让子类决定实例化哪一个类。工厂方法使一个类的实例化延迟到其子类。 C# 代码实现 以下是C#中实现工厂方法模式的一个简单示例: 首先,定义一个抽象产品(Product)类,它是所有具体产品的基类。 pu…...

程序员的能力-如何成为不会过时的“码农”

码农是指从事编程工作的人&#xff0c;也被称为程序员或开发者。他们使用计算机语言和工具来编写、测试和维护软件程序或网站。码农通常需要具备扎实的计算机科学知识、编程技能和问题解决能力&#xff0c;以及良好的逻辑思维和团队合作能力。他们可以在软件开发公司、科技企业…...

【OpenAI】自定义GPTs应用(GPT助手应用)及外部API接口请求

11月10日&#xff0c;OpenAI正式宣布向所有ChatGPT Plus用户开放GPTs功能 简而言之&#xff1a;GPT应用市场(简称GPTs, 全称GPT Store) Ps&#xff1a; 上图为首次进入时的页面&#xff0c;第一部分是自己创建的GPTs应用&#xff0c;下面是公开可以使用的GPTs应用 一、创建GPTs…...

canvas绘制不同样式的五角星(图文示例)

查看专栏目录 canvas实例应用100专栏&#xff0c;提供canvas的基础知识&#xff0c;高级动画&#xff0c;相关应用扩展等信息。canvas作为html的一部分&#xff0c;是图像图标地图可视化的一个重要的基础&#xff0c;学好了canvas&#xff0c;在其他的一些应用上将会起到非常重…...

C#: BitConverter 字节数组byte[ ] 转各种数据类型用法列举

说明&#xff1a;C# BitConverter 字节数组byte[ ] 转各种数据类型用法示例 1.ToBoolean(byte[] value, int startIndex)&#xff1a;将指定字节数组中从指定索引开始的两个字节转换为布尔值。 byte[] bytes { 1, 0 }; bool result BitConverter.ToBoolean(bytes, 0); // 输…...

【开发实践】前端jQuery+gif图片实现载入界面

一、需求分析 载入界面&#xff08;Loading screen&#xff09;是指在计算机程序或电子游戏中&#xff0c;当用户启动应用程序或切换到新的场景时&#xff0c;显示在屏幕上的过渡界面。它的主要作用是向用户传达程序正在加载或准备就绪的信息&#xff0c;以及提供一种视觉上的反…...

解析消费全返:谈谈那些关于商业的小妙招

每天五分钟讲解商业模式&#xff0c;大家好我是模式策划啊浩。 在数字化时代&#xff0c;商业模式正在经历前所未有的变革。其中&#xff0c;消费全返的概念正在逐渐崭露头角&#xff0c;引领着商业创新的新潮流。消费全返&#xff0c;顾名思义&#xff0c;是指消费者在购买商…...

如何在MinIO存储服务中通过Buckets实现远程访问管理界面上传文件

文章目录 前言1. 创建Buckets和Access Keys2. Linux 安装Cpolar3. 创建连接MinIO服务公网地址4. 远程调用MinIO服务小结5. 固定连接TCP公网地址6. 固定地址连接测试 前言 MinIO是一款高性能、分布式的对象存储系统&#xff0c;它可以100%的运行在标准硬件上&#xff0c;即X86等…...

算法 - 二分法 / 双指针 / 三指针 / 滑动窗口

文章目录 &#x1f37a; 二分法&#x1f37b; 旋转数组&#x1f942; 33. 搜索旋转排序数组 [旋转数组] [目标值] (二分法) &#x1f37b; 元素边界&#x1f942; 34. 在排序数组中查找元素的第一个和最后一个位置 [有序数组] > [元素边界] > (二分法)&#x1f942; 81. …...

ChatGPT3.5、GPT4.0、DALL·E 3和Midjourney对话与绘画智能体验

MidTool&#xff08;https://www.aimidtool.com/&#xff09;是一个集成了多种先进人工智能技术的助手&#xff0c;它融合了ChatGPT3.5、GPT4.0、DALLE 3和Midjourney等不同的智能服务&#xff0c;提供了一个多功能的体验。下面是这些技术的简要介绍&#xff1a; ChatGPT3.5&am…...

MySQL中锁的概述

按照锁的粒度来分可分为&#xff1a;全局锁&#xff08;锁住当前数据库的所有数据表&#xff09;&#xff0c;表级锁&#xff08;锁住对应的数据表&#xff09;&#xff0c;行级锁&#xff08;每次锁住对应的行数据&#xff09; 加全局锁&#xff1a;flush tables with read lo…...

5396. 棋盘

5396. 棋盘 - AcWing题库 二维差分数组 #include <iostream> #include <vector> using namespace std;int main() {int n, m;cin >> n >> m;vector<vector<int>> v(n 2, vector<int>(n 2));while (m--) {int x1, x2, y1, y2;cin…...

阿里云地域和可用区分布表,2024更新

2024年阿里云服务器地域分布表&#xff0c;地域指数据中心所在的地理区域&#xff0c;通常按照数据中心所在的城市划分&#xff0c;例如华北2&#xff08;北京&#xff09;地域表示数据中心所在的城市是北京。阿里云地域分为四部分即中国、亚太其他国家、欧洲与美洲和中东&…...

Pandas实战100例 | 案例 49: 数值运算

案例 49: 数值运算 知识点讲解 Pandas 提供了进行基本数学运算的简便方法,允许你在 DataFrame 的列之间执行加法、减法、乘法和除法等操作。 数值运算: 直接对 DataFrame 的列应用算术运算符(+, -, *, /)可以执行相应的数值运算。示例代码 # 准备数据和示例代码的运行结果…...

OSI七层协议和五层协议

【 1 】互联网协议交互的基础 硬件设备 光缆 【 2 】OSI七层协议 物理层&#xff08;Physical Layer&#xff09;&#xff1a;负责传输比特流&#xff08;0和1&#xff09;以及物理连接的建立和维护。数据链路层&#xff08;Data Link Layer&#xff09;&#xff1a;提供可…...

深度学习记录--归—化输入特征

归化 归化输入(normalizing inputs),对特征值进行一定的处理&#xff0c;可以加速神经网络训练速度 步骤 零均值化 通过x值更新让均值稳定在零附近&#xff0c;即为零均值化 归化方差 适当减小变量方差 解释 归化可以让原本狭长的数据图像变得规整&#xff0c;梯度下降的…...

Go Build编译打包文件

Go编译打包文件 1、简单打包 程序 main1.go&#xff1a; package mainimport "fmt"func main() {fmt.Println("Hello World!") }打包&#xff1a; # 在linux服务上执行下面的3个命令 # linux平台,生成main1可执行程序 CGO_ENABLED0 GOOSlinux GOARCHam…...

Java网络编程:概述--快速入门

I. 介绍 1.1 什么是网络编程 - 网络编程是指通过计算机网络实现程序之间的通信。在Java中&#xff0c;网络编程通常涉及到数据的传输、通信协议的使用以及与网络相关的各种操作。 1.2. 为什么学习Java网络编程 - Java网络编程是Java开发者重要的技能之一&#xff0c;因为它允许…...

Chapter03-Authentication vulnerabilities

文章目录 1. 身份验证简介1.1 What is authentication1.2 difference between authentication and authorization1.3 身份验证机制失效的原因1.4 身份验证机制失效的影响 2. 基于登录功能的漏洞2.1 密码爆破2.2 用户名枚举2.3 有缺陷的暴力破解防护2.3.1 如果用户登录尝试失败次…...

进程地址空间(比特课总结)

一、进程地址空间 1. 环境变量 1 &#xff09;⽤户级环境变量与系统级环境变量 全局属性&#xff1a;环境变量具有全局属性&#xff0c;会被⼦进程继承。例如当bash启动⼦进程时&#xff0c;环 境变量会⾃动传递给⼦进程。 本地变量限制&#xff1a;本地变量只在当前进程(ba…...

Zustand 状态管理库:极简而强大的解决方案

Zustand 是一个轻量级、快速和可扩展的状态管理库&#xff0c;特别适合 React 应用。它以简洁的 API 和高效的性能解决了 Redux 等状态管理方案中的繁琐问题。 核心优势对比 基本使用指南 1. 创建 Store // store.js import create from zustandconst useStore create((set)…...

Opencv中的addweighted函数

一.addweighted函数作用 addweighted&#xff08;&#xff09;是OpenCV库中用于图像处理的函数&#xff0c;主要功能是将两个输入图像&#xff08;尺寸和类型相同&#xff09;按照指定的权重进行加权叠加&#xff08;图像融合&#xff09;&#xff0c;并添加一个标量值&#x…...

【磁盘】每天掌握一个Linux命令 - iostat

目录 【磁盘】每天掌握一个Linux命令 - iostat工具概述安装方式核心功能基础用法进阶操作实战案例面试题场景生产场景 注意事项 【磁盘】每天掌握一个Linux命令 - iostat 工具概述 iostat&#xff08;I/O Statistics&#xff09;是Linux系统下用于监视系统输入输出设备和CPU使…...

多模态商品数据接口:融合图像、语音与文字的下一代商品详情体验

一、多模态商品数据接口的技术架构 &#xff08;一&#xff09;多模态数据融合引擎 跨模态语义对齐 通过Transformer架构实现图像、语音、文字的语义关联。例如&#xff0c;当用户上传一张“蓝色连衣裙”的图片时&#xff0c;接口可自动提取图像中的颜色&#xff08;RGB值&…...

Java入门学习详细版(一)

大家好&#xff0c;Java 学习是一个系统学习的过程&#xff0c;核心原则就是“理论 实践 坚持”&#xff0c;并且需循序渐进&#xff0c;不可过于着急&#xff0c;本篇文章推出的这份详细入门学习资料将带大家从零基础开始&#xff0c;逐步掌握 Java 的核心概念和编程技能。 …...

论文笔记——相干体技术在裂缝预测中的应用研究

目录 相关地震知识补充地震数据的认识地震几何属性 相干体算法定义基本原理第一代相干体技术&#xff1a;基于互相关的相干体技术&#xff08;Correlation&#xff09;第二代相干体技术&#xff1a;基于相似的相干体技术&#xff08;Semblance&#xff09;基于多道相似的相干体…...

NPOI操作EXCEL文件 ——CAD C# 二次开发

缺点:dll.版本容易加载错误。CAD加载插件时&#xff0c;没有加载所有类库。插件运行过程中用到某个类库&#xff0c;会从CAD的安装目录找&#xff0c;找不到就报错了。 【方案2】让CAD在加载过程中把类库加载到内存 【方案3】是发现缺少了哪个库&#xff0c;就用插件程序加载进…...

springboot 日志类切面,接口成功记录日志,失败不记录

springboot 日志类切面&#xff0c;接口成功记录日志&#xff0c;失败不记录 自定义一个注解方法 import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target;/***…...