【C++庖丁解牛】STL简介 | string容器初次见面


📙 作者简介 :RO-BERRY
📗 学习方向:致力于C、C++、数据结构、TCP/IP、数据库等等一系列知识
📒 日后方向 : 偏向于CPP开发以及大数据方向,欢迎各位关注,谢谢各位的支持


请添加图片描述


目录

  • 1. 什么是STL
  • 2. STL的版本
  • 3. STL的六大组件
  • 4. STL的重要性
  • 5. 如何学习STL
  • 6.STL的缺陷
  • 7. 为什么学习string类?
  • 8. 标准库中的string类
    • 8.1 string类(了解)
    • 8.2 string类的常用接口说明(注意下面我只讲解最常用的接口)
    • 8.3 string类对象的容量操作
    • 8.4 测试string容量相关的接口
      • 📖size、length和capacity
      • 📖clear接口
      • 📖resize接口
      • 📖reserve接口
      • 📖empty接口
    • 8.5 string类对象的访问及遍历操作
      • 反向迭代器
      • const迭代器


1. 什么是STL

STL(standard template libaray-标准模板库):是C++标准库的重要组成部分,不仅是一个可复用的组件库,而且是一个包罗数据结构与算法的软件框架。

2. STL的版本

  • 原始版本
    Alexander Stepanov、Meng Lee 在惠普实验室完成的原始版本,本着开源精神,他们声明允许任何人任意运用、拷贝、修改、传播、商业使用这些代码,无需付费。唯一的条件就是也需要向原始版本一样做开源使用。 HP 版本–所有STL实现版本的始祖。
  • P. J. 版本
    由P. J. Plauger开发,继承自HP版本,被Windows Visual C++采用,不能公开或修改,缺陷:可读性比较低,
    符号命名比较怪异。
  • RW版本
    由Rouge Wage公司开发,继承自HP版本,被C+ + Builder 采用,不能公开或修改,可读性一般。
  • SGI版本
    由Silicon Graphics Computer Systems,Inc公司开发,继承自HP版 本。被GCC(Linux)采用,可移植性好,可公开、修改甚至贩卖,从命名风格和编程 风格上看,阅读性非常高。我们后面学习STL要阅读部分源代码,主要参考的就是这个版本。

3. STL的六大组件

在这里插入图片描述

4. STL的重要性

STL(Standard Template Library)是C++标准库中的一个重要组成部分,它提供了一系列的通用模板类和函数,用于实现常用的数据结构和算法。STL的重要性主要体现在以下几个方面:

  1. 提高开发效率:STL提供了丰富的容器(如vector、list、map等)和算法(如排序、查找、遍历等),可以直接使用这些现成的模板,避免了手动实现这些功能的繁琐过程,大大提高了开发效率。

  2. 提供高性能的数据结构和算法:STL中的容器和算法都经过精心设计和优化,具有高效的性能。例如,vector提供了快速的随机访问和动态扩容的能力,而算法库中的排序和查找算法采用了高效的实现方式,可以在大规模数据处理中获得较好的性能。

  3. 代码可重用性:STL中的容器和算法都是通用的,可以适用于各种类型的数据。通过使用STL,我们可以编写出更加通用、可复用的代码,提高代码的可维护性和可扩展性。

  4. 标准化和规范化:STL是C++标准库的一部分,它定义了一套统一的接口和规范,使得不同的开发者可以使用相同的方式来操作数据结构和算法。这样可以提高代码的可读性和可理解性,方便代码的交流和共享。

  5. 丰富的功能和灵活性:STL提供了多种容器和算法的选择,可以根据具体的需求选择合适的容器和算法。同时,STL还支持自定义类型的容器和算法,可以根据实际情况进行扩展和定制。

在工作中
网上有句话说:“不懂STL,不要说你会C++”。STL是C++中的优秀作品,有了它的陪伴,许多底层的数据结构以及算法都不需要自己重新造轮子,站在前人的肩膀上,健步如飞的快速开发。

5. 如何学习STL

学习STL(Standard Template Library)是C++程序员的重要一步,它提供了一组通用的数据结构和算法,可以大大提高代码的复用性和开发效率。以下是学习STL的一些建议:

  1. 理解STL的组成部分:STL由容器(Containers)、迭代器(Iterators)和算法(Algorithms)三个主要组成部分构成。容器用于存储数据,迭代器用于访问容器中的元素,算法用于对容器中的元素进行操作和处理。

  2. 学习STL的容器:STL提供了多种容器,如vector、list、set、map等。每种容器都有自己的特点和适用场景,需要了解它们的特性、操作方法和性能特点。

  3. 掌握STL的迭代器:迭代器是STL中非常重要的概念,它提供了一种统一的访问容器元素的方式。了解迭代器的种类和使用方法,能够灵活地遍历和操作容器中的元素。

  4. 熟悉STL的算法:STL提供了丰富的算法,如排序、查找、变换等。学习这些算法的使用方法和适用场景,能够快速地解决各种常见的问题。

  5. 阅读STL的源码和文档:阅读STL的源码可以深入理解其实现原理和设计思想,同时也可以学习到一些高效的编程技巧。此外,还可以参考STL的官方文档或相关书籍,了解更多细节和使用技巧。

  6. 实践和练习:通过实际的项目或练习题来应用STL,加深对其的理解和掌握。可以尝试使用STL解决一些常见的问题,提高自己的编程能力。

简单总结一下:学习STL的三个境界:能用,明理,能扩展 。

6.STL的缺陷

  1. STL库的更新太慢了。这个得严重吐槽,上一版靠谱是C++98,中间的C++03基本一些修订。C++11出
    来已经相隔了13年,STL才进一步更新。
  2. STL现在都没有支持线程安全。并发环境下需要我们自己加锁。且锁的粒度是比较大的。
  3. STL极度的追求效率,导致内部比较复杂。比如类型萃取,迭代器萃取。
  4. STL的使用会有代码膨胀的问题,比如使用vector/vector/vector这样会生成多份代码,当然这是模板语法本身导致的。

7. 为什么学习string类?

学习string类是因为它是C++中用于处理字符串的重要类之一。使用string类可以方便地进行字符串的操作和处理,包括字符串的连接、截取、查找、替换等。相比于C风格的字符串处理函数,string类提供了更多的功能和便利性。

通过学习string类,你可以掌握以下知识点:

  • 字符串的创建和初始化:可以使用构造函数或者赋值操作符来创建和初始化string对象。
  • 字符串的基本操作:可以使用成员函数来获取字符串的长度、访问特定位置的字符、比较字符串等。
  • 字符串的连接和拼接:可以使用加号运算符或者成员函数来实现字符串的连接和拼接。
  • 字符串的截取和提取:可以使用成员函数来截取子串或者提取特定位置的字符。
  • 字符串的查找和替换:可以使用成员函数来查找子串或者替换特定字符或子串。
  • 字符串的转换和格式化:可以使用成员函数来实现字符串与其他数据类型之间的转换,以及字符串的格式化输出。

总之,学习string类可以帮助你更加高效地处理字符串,提高编程效率和代码可读性。
C语言中,字符串是以’\0’结尾的一些字符的集合,为了操作方便,C标准库中提供了一些str系列的库函数,但是这些库函数与字符串是分离开的,不太符合OOP的思想,而且底层空间需要用户自己管理,稍不留神可能还会越界访问。

8. 标准库中的string类

8.1 string类(了解)

可以自行查看一下string类的文档介绍

  1. 字符串是表示字符序列的类
  2. 标准的字符串类提供了对此类对象的支持,其接口类似于标准字符容器的接口,但添加了专门用于操作单字节字符字符串的设计特性。
  3. string类是使用char(即作为它的字符类型,使用它的默认char_traits和分配器类型(关于模板的更多信息,请参阅basic_string)。
  4. string类是basic_string模板类的一个实例,它使用char来实例化basic_string模板类,并用char_traits和allocator作为basic_string的默认参数(根于更多的模板信息请参考basic_string)。
  5. 注意,这个类独立于所使用的编码来处理字节:如果用来处理多字节或变长字符(如UTF-8)的序列,这个类的所有成员(如长度或大小)以及它的迭代器,将仍然按照字节(而不是实际编码的字符)来操作。

总结:

  1. string是表示字符串的字符串类
  2. 该类的接口与常规容器的接口基本相同,再添加了一些专门用来操作string的常规操作。
  3. string在底层实际是:basic_string模板类的别名,typedef basic_string<char, char_traits, allocator> string;
  4. 不能操作多字节或者变长字符的序列。

在使用string类时,必须包含#include头文件以及using namespace std;

8.2 string类的常用接口说明(注意下面我只讲解最常用的接口)

  1. string类对象的常见构造
(constructor)函数名称功能说明
string() (重点)构造空的string类对象,即空字符串
string(const char* s) (重点)用C-string来构造string类对象
string(size_t n, char c)string类对象中包含n个字符c
string(const string&s) (重点)拷贝构造函数

这里重点示范三个重点的string构造:

#include<iostream>
using namespace std;int main()
{string s1; // 构造空的string类对象s1string s2("hello world"); // 用C格式字符串构造string类对象s2string s3(s2); // 拷贝构造s3cout << s1 << endl;cout << s2 << endl;cout << s3 << endl;return 0;
}

运行结果:

在这里插入图片描述

8.3 string类对象的容量操作

函数名称功能说明
size(重点)返回字符串有效字符长度
length返回字符串有效字符长度
capacity返回空间总大小
empty (重点)检测字符串释放为空串,是返回true,否则返回false
clear (重点)清空有效字符
reserve (重点)为字符串预留空间
resize (重点)将有效字符的个数该成n个,多出的空间用字符c填充

8.4 测试string容量相关的接口

📖size、length和capacity

sizelength都可以输出string容器中存储的字符串长度
capacitystring容器的容量

int main()
{// 注意:string类对象支持直接用cin和cout进行输入和输出string s("hello, world!!!");cout << s.size() << endl;cout << s.length() << endl;cout << s.capacity() << endl;cout << s << endl;
}

在这里插入图片描述

📖clear接口

将s中的字符串清空,注意清空时只是将size清0,不改变底层空间的大小

int main()
{string s("hello, world!!!");s.clear();cout << s.size() << endl;cout << s.capacity() << endl;
}

在这里插入图片描述

📖resize接口

list容器的resize()函数用于改变容器的大小。它接受一个参数,该参数表示容器的新大小。

当新大小小于当前大小时,resize()函数会删除多余的元素,使容器的大小等于新大小。
当新大小大于当前大小时,resize()函数会在容器末尾添加默认构造的元素,直到容器的大小等于新大小。

  • 将s中有效字符个数增加到10个,多出位置用’a’进行填充
int main()
{string s("hello");s.resize(10, 'a');cout << s.size() << endl;cout << s.capacity() << endl;cout << s << endl;
}

在这里插入图片描述

  • 将s中有效字符个数增加到15个,多出位置用缺省值’\0’进行填充
int main()
{string s("hello");s.resize(15);cout << s.size() << endl;cout << s.capacity() << endl;cout << s << endl;
}

在这里插入图片描述

  • 将s中有效字符个数缩小到5个
int main()
{string s("hello world");s.resize(5);cout << s.size() << endl;cout << s.capacity() << endl;cout << s << endl;
}

在这里插入图片描述

📖reserve接口

reserve()是list容器的一个成员函数,用于预留一定的内存空间,以提高插入元素的效率。
reserve()函数的作用是为list容器预留一定数量的元素空间,但并不实际创建这些元素。它可以在插入大量元素之前使用,以避免频繁的内存重新分配和复制操作,从而提高性能。

使用reserve()函数的语法如下:

void reserve(size_type n);
其中,n表示要预留的元素数量。

注意 :reserve()函数只会增加容器的容量,并不会改变容器的大小。如果在调用reserve()之后插入的元素数量超过了预留的空间,容器会自动进行内存重新分配。

int main()
{string s;cout << s.size() << endl;cout << s.capacity() << endl;// 测试reserve是否会改变string中有效元素个数s.reserve(100);cout << s.size() << endl;cout << s.capacity() << endl;// 测试reserve参数小于string的底层空间大小时,是否会将空间缩小s.reserve(50);cout << s.size() << endl;cout << s.capacity() << endl;
}

在这里插入图片描述

📖empty接口

检测字符串释放为空串,是返回true,否则返回false

int main()
{string s;int i = s.empty();cout << i << endl;s = "abcd";i = s.empty();cout << i << endl;return 0;
}

在这里插入图片描述
注意:

  1. size()与length()方法底层实现原理完全相同,引入size()的原因是为了与其他容器的接口保持一致,一般情况下基本都是用size()。
  2. clear()只是将string中有效字符清空,不改变底层空间大小。
  3. resize(size_t n) 与 resize(size_t n, char c)都是将字符串中有效字符个数改变到n个,不同的是当字符个数增多时:resize(n)用0来填充多出的元素空间,resize(size_t n, char c)用字符c来填充多出的元素空间。注意:resize在改变元素个数时,如果是将元素个数增多,可能会改变底层容量的大小,如果是将元素个数减少,底层空间总大小不变。
  4. reserve(size_t res_arg=0):为string预留空间,不改变有效元素个数,当reserve的参数小于string的底层空间总大小时,reserver不会改变容量大小。

8.5 string类对象的访问及遍历操作

函数名称功能说明
operator[] (重点)返回pos位置的字符,const string类对象调用
begin+ endbegin获取一个字符的迭代器 + end获取最后一个字符下一个位置的迭代器
rbegin + rendbegin获取一个字符的迭代器 + end获取最后一个字符下一个位置的迭代器
范围forC++11支持更简洁的范围for的新遍历方式

注意:
string遍历时使用最多的还是for+下标 或者 范围for(C++11后才支持)

void Teststring4()
{string s("hello Bit");// 3种遍历方式:// 需要注意的以下三种方式除了遍历string对象,还可以遍历是修改string中的字符,// 另外以下三种方式对于string而言,第一种使用最多// 1. for+operator[]for (size_t i = 0; i < s.size(); ++i)cout << s[i] << endl;//等价于 cout << s.operator[i] << endl;// 2.迭代器string::iterator it = s.begin();while (it != s.end()){cout << *it << endl;++it;}// string::reverse_iterator rit = s.rbegin();// C++11之后,直接使用auto定义迭代器,让编译器推到迭代器的类型auto rit = s.rbegin();while (rit != s.rend())cout << *rit << endl;// 3.范围forfor (auto ch : s)cout << ch << endl;
}

我们最推荐使用的是迭代器,其重要作用会在后续章节体现

反向迭代器

我们有正向的迭代器还有反向的
在这里插入图片描述

rbegin

在这里插入图片描述

rend

在这里插入图片描述

我们可以使用rbegin和rend进行反向输出

int main()
{string s("hello world");string::reverse_iterator it = s.rbegin();while (it != s.rend()){cout << *it << "";++it;}cout << endl;return 0;
}

在这里插入图片描述

const迭代器

const迭代器是一种用于遍历容器中元素的迭代器,它的作用是限制对容器中元素的修改操作。通过使用const迭代器,我们可以确保在遍历容器时不会意外地修改容器中的元素。

const迭代器有以下几个特点:

  1. 只能读取容器中的元素,不能修改它们。
  2. 可以与普通迭代器进行区分,以便在编程中进行类型检查和约束。
  3. 可以用于遍历常量容器,例如const vector、const list等。

对const对象使用迭代器的时候,也需要用const迭代器,这是针对const对象特定的迭代器

int main()
{const string s("hello world");string::const_reverse_iterator it = s.rbegin();while (it != s.rend()){cout << *it << "";++it;}cout << endl;return 0;
}

在这里插入图片描述
对于正向的迭代器用法是一样的

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

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

相关文章

2024年AI辅助研发趋势:AI辅助科技发展

目录 前言 一、AI辅助研发的技术进展 &#xff08;一&#xff09;深度学习在研发中的应用 &#xff08;二&#xff09;强化学习在研发中的应用 &#xff08;三&#xff09;生成模型在研发中的应用 &#xff08;四&#xff09;技术如何推动研发效率的提升 二、2024人工智…

华为设备小型园区网方案(有线+无线+防火墙)

&#xff08;一&#xff09;配置有线部分 1.配置LSW2 &#xff08;1&#xff09;创建相关vlan [LSW2]vlan batch 10 3000 &#xff08;2&#xff09;配置连接LSW1的Eth-Trunk1&#xff0c;透传VLAN 10 3000 [LSW2]int Eth-Trunk 1 [LSW2-Eth-Trunk1]port link-type trunk [LSW2…

神经网络的矢量化,训练与激活函数

我们现在再回到我们的神经元部分&#xff0c;来看我们如何用python进行正向传递。 单层的正向传递&#xff1a; 我们回到我们的线性回归的函数。我们每个神经元通过上述的方法&#xff0c;就可以得到我们的激发值&#xff0c;从而可以继续进行下一层。 我们用这个方法就可以得…

AES加密——AES加密原理与C++实现AES加密

概述 在密码学中&#xff0c;加密算法被分为两种主要类型&#xff1a;单向加密和双向加密。单向加密算法是不可逆的&#xff0c;主要用于数据完整性验证和密码存储&#xff0c;其中包括MD5、SHA等摘要算法。双向加密算法允许加密和解密过程&#xff0c;分为对称加密和非对称加…

Viper反序列化解析字段不成功问题

问题背景 通过viper解析文件内容映射config一直失败&#xff0c;相关代码如下 type Config struct {DBConf *DBConf toml:"db"RedisConf *RedisConf toml:"redis"WebConfig *WebConfig toml:"app" }type DBConf struct {Read struct {Ds…

通过一篇文章带你玩转git和GitHub

Git和Github的基本用法 前言一、Git和Github的基本用法背景下载安装安装 git for windows安装 tortoise gitgit安装过程中的一些选项 tortoise git汉化教程下载tortoise git汉化安装包安装tortoise git汉化安装包 三、使用 Github 创建项目注册账号创建项目下载项目到本地 四、…

Excel转pdf

1、excel-内存值--Workbook 转pdf /** * excel To pdf * * param outPath 输出路径 * param workbook excel-内存值 * throws IOException */ public static void excelToPdf(String outPath,Workbook workbook) throws IOException, DocumentException { Document documentnul…

突然发现一个很炸裂的平台!

平时小孟会开发很多的项目&#xff0c;很多项目不仅开发的功能比较齐全&#xff0c;而且效果比较炸裂。 今天给大家介绍一个我常用的平台&#xff0c;因含低代码平台&#xff0c;开发相当的快。 1&#xff0c;什么是低代码 低代码包括两种&#xff0c;一种低代码&#xff0c;…

Java中的常用类(三)

一、正则表达式 正则表达式 regex&#xff0c;全称Regular Expression。正则表达式是一种规则&#xff08;模式&#xff09;匹配语法 可以使用一些正则表达式中的特殊符号来定义一种规则&#xff0c;然后用此规则匹配某个字符&#xff0c;如果字符串与规则匹配则返回true&…

【Docker1】Docker镜像和容器基本操作

Docker基本管理一、Docker概述1、为什么要用到容器&#xff1f;2、Docker是什么&#xff1f;3、Docker的设计宗旨4、容器的优点5、Docker与虚拟机的区别6、Docker的三大核心概念 二、安装Docker1、yum安装2、二进制安装 三、Docker镜像创建与操作1、Docker 镜像操作1.1 搜索镜像…

【JavaEE进阶】Spring中事务的实现

文章目录 &#x1f343;前言&#x1f334;事务简介&#x1f6a9; 什么是事务?&#x1f6a9;为什么需要事务?&#x1f6a9;事务的操作 &#x1f340;Spring 中事务的实现&#x1f6a9;Spring 编程式事务&#x1f6a9;Spring声明式事务Transactional&#x1f6a9;Transactional…

数字人民币钱包(二)

文章目录 前言一 什么是数字人民币钱包&#xff1f;二 怎么开通数字人民币钱包&#xff1f;三 数字人民币钱包有哪些&#xff1f;四 数字人民币钱包升级 前言 上篇文章梳理了什么是数字人民币&#xff0c;及其特征和相关概念&#xff0c;这篇文章来整理下数字人民币钱包。数字人…

selenium常用操作汇总

本文总结使用selenium进行web/UI自动化时&#xff0c;会用到的一些常用操作。 定位元素 driver.find_element_by_xpath()#1、绝对路径 2、元素属性 3、层级和属性结合 4、使用逻辑运算符 driver.find_element_by_id()#根据id定位&#xff0c;HTML规定id属性在HTML文档中必须是唯…

App拉起微信小程序参考文章

App拉起微信小程序参考文章h5页面跳转小程序-----明文URL Scheme_weixin://dl/business/?appid*appid*&path*path*&qu-CSDN博客文章浏览阅读561次&#xff0c;点赞16次&#xff0c;收藏5次。仅需两步&#xff0c;就能实现h5跳转小程序&#xff0c;明文 URL Scheme&…

vue2 vue-cli vue-router vuex

Vue2 插值表达式 利用表达式进行插值渲染&#xff0c;将数据渲染到页面中。 语法&#xff1a;{{ 表达式 }} PS&#xff1a; 使用的数据要存在支持的是表达式&#xff0c;不是语句 if、for不能在标签属性中使用{{ }} v-show和v-if v-show底层原理&#xff1a;切换css的dis…

SRC学习-成为赏金猎人

你是否对漏洞挖掘充满好奇&#xff1f;零基础或有基础但想更进一步&#xff1f;想赚取可观的漏洞赏金让自己有更大的自由度&#xff1f; 那么&#xff0c;不妨了解下土拨鼠的安全屋 这或许也是你成为漏洞赏金猎人的第一课。 逻辑漏洞挖掘手法与创新思路&#xff0c;带你突破…

@EnableWebMvc介绍和使用详细demo

EnableWebMvc是什么 EnableWebMvc 是 Spring MVC 中的一个注解&#xff0c;它用于启用 Spring MVC 框架的基本功能&#xff0c;以便你可以使用 Spring MVC 提供的特性来处理 Web 请求。 通常情况下&#xff0c;在基于 Spring Boot 的应用中&#xff0c;并不需要显式地使用 Ena…

GC--垃圾回收

目录 垃圾回收概念 什么是垃圾? 垃圾回收机制什么时候会进行GC&#xff1f;&#xff1f; 应该关心垃圾回收那些哪些区域的回收 垃圾回收相关算法 垃圾回收算法&#xff1a;[标记阶段、回收阶段] 垃圾标记阶段 标记阶段的目的 引用计数算法&#xff08;目前没有在使用&…

实现类似 Word 协同编辑--Canvas-Editor

前言 对于word的协同编辑&#xff0c;已经构思很久了&#xff0c;但是没有找到合适的插件。今天推荐基于canvas/svg 的富文本编辑器 canvas-editor&#xff0c;能实现类似word的基础功能&#xff0c;如果后续有更好的&#xff0c;也会及时更新。 Canvas-Editor效果图: 官方文…

FFmpeg--AAC音频解码流程

文章目录 AAC 组成函数分析读aac帧写aac帧aac的head参数设置 运行结果 AAC 组成 AAC音频格式&#xff1a;是⼀种由MPEG-4标准定义的有损⾳频压缩格式 ADTS:是AAC音频的传输流格式 AAC音频文件的每一帧由ADTS Header和AAC Audio Data组成 每⼀帧的ADTS的头⽂件都包含了⾳频的采…