C++语言·string类

1. 为什么有string类

        C语言中,字符串是以'\0'结尾的一些字符的集合,为了操作方便,C标准库中提供了一些str系列的库函数(strcpy,strcat),但是这些库函数与字符串是分离开的,不太符合OOP(Object Oriented Programming面向对象编程)的思想,而且底层空间需要用户自己管理,稍不留神可能还会越界访问。

        所以在C++中用string类统一管理字符串和其方法,简化编程。其实string并不是一个正经的STL库中的内容,它的出现比STL略早,内容也没有STL中的别的模块成熟。

2. 标准库中的string类

2.1 string类

        官网资料:string - C++ Reference

        string是一个管理char的类模板,是一个管理字符的顺序表,或者说是一个字符数组。

        该类的接口与常规容器的接口基本相同,再添加了一些专门用来操作string的常规操作,容器就是指栈、队列这些写好了可以装数据的东西。

        在使用string类时,要包含它的头文件 <string> 

2.2 string类的常用接口说明

2.2.1 string类的常见构造

        官网资料:string::string - C++ Reference

        98版中有7种构造方案其中1、2、4是比较常用的。

        1号构造:就是默认构造,会构造一个长度为0的空字符串

        2号、4号构造:拷贝构造,只不过参数不同,一个是string类型,一个是C字符串

        3号构造:从pos位置拷贝len个字符去构造,如果字符串较短,就能拷几个就拷几个。npos是一个size_t类型的-1,也就是24亿多的一个数,用这样一个字符串不可能达到的长度作为len的缺省值,其意义就是在不传len参的时候拷贝到字符串结尾

        5号构造:将一个C字符串的前n个字符拷贝构造

        6号构造:用n个字符c构造

        7号构造:用另一个string类对象的迭代区间构造

                        

        可能有的同学已经发现了我上面打印string的时候用的是流插入 << 操作符,当然是因为这个string类中为了方便我们进行打印写了友元重载函数。

2.2.2 string类对象的容量操作

2.2.2.1 size 与 length 与 capacity

        size 返回字符串有效数据个数(有效字符长度),不包括 '\0'

        length 返回字符串有效字符长度,不包括 '\0'

        那为什么要设计两个功能一样的成员函数呢,实际上这就是设计上的失误,在之后我们学的各种容器中,都是只有size没有length,length的出现只是一个特例。为了保持一致,今后我们也只使用size

        capacity 返回该string的容量,或者说string总空间的大小,因为string类中存了不止字符串本身的内容,所以其实际长度一定不等于字符串长度

                

        不过不用担心string的容量不够,string会自己扩容的,换句话说,当这个capacity填满了,就会扩容到更大的capacity。

2.2.2.2 empty 与 clear

        clear 清空有效字符

        empty 检测字符串是否为空串,是空返回true,不是空返回false

                  

2.2.2.3 reserve 与 resize

        reserve是给string扩容的,直接改变capacity的大小,当我们知道一个string需要多大空间的时候就可以提前reserve,把这块空间开好。当然,reserve改变capacity的大小,因此也可以缩容,但是VS下不支持缩容操作。

        注意,reserve(保留)  reverse(逆转),这俩个函数要分清楚,逆转函数reverse是算法函数,其参数是两个迭代器,用来控制将容器中迭代器所划分出来的数据顺序反转,如果用在string身上的含义就是反转字符串。

        resize 将有效字符的个数改成n个,多出的空间用选定的字符c填充,如果不指定字符c,编译器就会自动补上默认字符 '\0'

        resize因为给字符串本身扩容了,所以它也会影响capacity

        如果用resize强制缩短字符串长度,会使多出的字符串删掉,但是不会影响capacity的大小                                

2.2.2.4 shrink_to_fit

        这个是正经的缩容接口,当我们把一个很长的字符串删除多次之后会出现很多空出来的空间,造成一定程度上的浪费,此时就用这个接口让 capacity 的大小更适应字符串长度 size

        但是不要频繁缩容,因为缩容的本质是将原本大空间中的东西拷贝到小空间中去,这个过程会造成时间上的消耗。

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

2.2.3.1 operator[]

        官网资料:https://legacy.cplusplus.com/reference/string/string/operator[]/

        经过对于操作符 [ ] 的重载,string类对象也可以像C字符串那样访问和操作,这种遍历方案明显简单于迭代器,但缺点就是不通用,链表和树中无法用这种方案遍历。

                

        我们看官网上对于这个运算符的重载声明:

        首先,返回值是一个引用,这是为了可以对字符串中提取出来的某个字符进行修改(第一行的声明)。

        第二,它重载了两个,一个是正常的,另一个带了const修饰,这是为了防止在使用 [ ] 操作一个const string类型的字符串时,用第一种重载就会出现权限放大的问题,所以用const修饰了this指针指向的内容,和重载函数的返回值。

 PS: 范围for遍历(C++11)

        说到遍历,我们前面还提过一种范围for的遍历方案,自动++,自动判断结束。

        范围for遍历所有容器都可以用,因为范围for的底层就是迭代器,但范围for每次拿出来的这个e还是s1中一次一次正在遍历的字符的拷贝,如果 auto& 加上引用之后就可以修改s1了。

                

2.2.3.2 at访问

        at访问与方括号[ ] 访问的区别在于,at越界会抛异常,而[ ]会断言。抛异常后面的章节会讲到,这个是可以更改的,但是断言报错就直接崩掉程序了。

2.2.3.3 begin end 与 迭代器 

        begin:任何容器中都是返回第一个数据位置的 iterator(迭代器)

        end:任何容器中都是返回最后一个有效数据下一个位置的 iterator(迭代器)

        iterator(迭代器):可以理解成一个类似指针的东西,由它来控制目前访问的是第几号数据。之前我们学过访问数组中的某号元素时,是用下标来控制,但是这种 下标引用操作符 [ ] 的使用是有限制的,只能作用于顺序表。但是迭代器就比较通用,可以作用于顺序表,也可以作用于链表或树。

        不同容器的迭代器的实现是不尽相同的,所以 iterator 存在于各个容器的类域中,所以使用时要带上类域,否则全局范围内是找不到这个迭代器的。

                        

        因为 \0 不属于有效字符,算是一种标志,所以end返回的迭代器指向的位置就是 \0 而不是 \0 的下一个位置。

        可以看到再使用迭代器的时候我们用 * 来修改迭代器指向的内容的,其实这里是重载了 * 操作符,使得迭代器用起来更像指针。其他容器也是这么用 * 修改迭代器内容的。

        如果 s1 是const修饰的只读字符串,那么迭代器就要写成与其匹配的只读迭代器 const_iterator 防止权限放大。

                        

2.2.3.4 rbegin rend 与 反向迭代器

        这个就是把正向迭代器的所有用法反过来而已

        rbegn:返回最后一个有效数据的迭代器

        rend:返回第一个有效数据的前一位置的迭代器

        reverse_iterator:反向迭代器,++向前走,反向迭代器也有const版本

                        

PS: 算法排序 sort

        讲到迭代器就要提及sort算法,它是用来给各种容器内的数据排序的,默认是从小到大

        官网资料:sort - C++ Reference

        使用 sort() 要包含头文件 <algorithm> (算法),因为sort要给各类容器排序所以它是用模板写的,传的参数就是容器的迭代器,用两个迭代器来画出一块 左闭右开 的区域,此时sort就会在这块区域中排序了

                                ​​​​​​​

2.2.4 string类对象的修改操作

2.2.4.1 push_back append 与 operator+=

        push_back: string::push_back - C++ Reference

        append: string::append - C++ Reference

        operator+=: string::operator+= - C++ Reference

        push_back() 一次只能在string类对象后面添加一个字符。append()可以添加字符串、另一个string的实例化、用下标圈出来或用迭代器圈出来的另一个string等等,总之构造时能实现的所有方案它都能实现,不过那个是构造,但append是添加。

        但是上面两种都很少使用,operator+=操作符重载多方便啊,可以添加字符,字符串,或另一个string对象。

                ​​​​​​​        

2.2.4.2 pop_back 与 erase

        pop_back: string::pop_back - C++ Reference

        erease: string::erase - C++ Reference

        pop_back还是一次只能尾删一个字符,不太好用,它存在的意义就是和其他容器保持一致。

        erease可以通过 下标 和 元素个数 来进行删除,也可以通过迭代器但是用的比较少,注意迭代区间永远是左闭右开

        ​​​​​​​        ​​​​​​​        

2.2.4.3 assign 重新赋值

        官网资料:string::assign - C++ Reference

        这个成员函数的功能就是将string对象中的原有内容都删掉然后放入新内容,参数用法和构造的用法完全一样,唯一的区别就是不能修改成空string,而构造可以构造空string。

        

2.2.4.4 insert 插入

        官网资料:string::insert - C++ Reference

        前面的 += 操作符重载为我们提供了给string实例尾插的方法,那么insert就提供了在string实例的任意位置插入的方法。

        pos位置,用来选择在哪个位置插入,iterator迭代器也可以选择插入的位置。插入的内容可以是 char* 这种以 \0 结尾的C语言风格的字符串,也可以是C++的string类。        

        唯一要注意的是要插入一个字符的时候,用 5 号重载,插入一个字符时要给 n 传参为1,表示要插入 1 个字符。不能像传字符串那样,丢一串字符串就完事了,不去给字符数量。

                        

2.2.4.5 replace 替换

        官网资料:string::replace - C++ Reference

        别看这玩意一大堆,其实就是让你指出string中的一块地方,可以把这块地方的内容替换成别的内容而已,只是给出的替换方案相当多。

        ​​​​​​​        ​​​​​​​        

2.2.5 string类的其他操作

2.2.5.1 c_str 获取字符串指针

        可能之后写代码的时候C和C++混用,但是C没有string类,所以我们就获取字符转的底层指针,用来写C的代码段。

2.2.5.2 find 与 substr

        官网资料:string::find - C++ Reference

        find接口的功能是从 pos 位置向后找字符 c ,返回该字符在字符串中的下标

        find接口一般与substr接口一起使用,用于取下来字符串中用分隔符分隔开的某串字符串

        官网资料:string::substr - C++ Reference

        substr接口从 pos 位置开始,向后截取 len 个字符,然后将其返回

        ​​​​​​​   

2.2.5.3 operator+

        之前的operator+=只能支持基础string在前,后面加上一个string、char*或char。

        但是operator+的出现满足了基础string可以在后

                        

2.2.5.3 getline

        官网资料:getline (string) - C++ Reference

        cin与scanf一样,遇到空格或者换行都会认为是结束标志,于是就停止提取了,那如何获取一句带有空格的一句话呢?

        在C的时候我们会使用到 fgets 那么在C++的话我们就会用到getlin,同时getline还允许我们自己设置提取结束符 delim

        ​​​​​​​        ​​​​​​​        

        可以看到getline不会像fgets那样从前向后覆盖字符串,而是先清空string再获取新字符串。

        

2.2.5.4 to_string 与 stoi

        官网资料:to_string - C++ Reference

        to_string可以将各种数值转化成string,其功能类似于C库中的 itoa

        官网资料:stoi - C++ Reference

        stoi可以将string转化成整形,其功能类似于C库中的 atoi

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

ARM(4)缓存一致性

目录 一、缓存一致性问题 二、一致性实现方案 2.1 目录一致性协议 2.2 嗅探一致性协议 三、CHI协议 3.1 cache state 3.2 snoop维护一致性 四、其他一致性协议 4.1 MSI协议 4.2 MESI 协议 4.3 MOESI协议 本文介绍以下内容&#xff1a; 缓存一致性问题一致性实现方案…

通过 Java 操作 redis -- zset 有序集合基本命令

目录 使用命令 zadd&#xff0c;zrange 使用命令 zcard 使用命令 zrem 使用命令 zscore 使用命令 zrank 关于 redis zset 有序集合类型的相关命令推荐看Redis - Zset 有序集合 要想通过 Java 操作 redis&#xff0c;首先要连接上 redis 服务器&#xff0c;推荐看通过 Jav…

景源畅信数字:抖音小店的入住门槛大不大?

近年来&#xff0c;随着短视频平台的崛起&#xff0c;抖音小店逐渐成为了众多商家和创业者关注的焦点。那么&#xff0c;抖音小店的入住门槛究竟大不大呢?本文将从四个方面对这一问题进行详细阐述。 一、注册流程 抖音小店的注册流程相对简单&#xff0c;只需按照官方指引完成…

渲染管线中光照的计算

文章目录 渲染管线中光照的计算前言法向量朗伯余弦定律漫反射环境光照镜面光照菲涅尔效应 表面粗糙度光照模型平行光源点光源衰减 聚光灯 渲染管线中光照的计算 前言 首先我们来看一下同一个模型在有光与无光下的区别&#xff1a; 无光&#xff1a; 有光 很明显的感知就是…

《ESP8266通信指南》14-连接WIFI(基于Lua)

往期 《ESP8266通信指南》13-Lua 简单入门&#xff08;打印数据&#xff09;-CSDN博客 《ESP8266通信指南》12-Lua 固件烧录-CSDN博客 《ESP8266通信指南》11-Lua开发环境配置-CSDN博客 《ESP8266通信指南》10-MQTT通信&#xff08;Arduino开发&#xff09;-CSDN博客 《ES…

【api接口开通教程】YouTube Data API v3申请流程

一、背景调查 1.1 API接口介绍 采集youtube数据&#xff0c;大体分为两种方案&#xff1a;一种是基于爬虫&#xff0c;一种是基于API接口。 说人话就是&#xff1a;爬虫相当于走后门、爬窗户&#xff08;利用技术手段窃取&#xff0c;人家没说给&#xff0c;但我硬拿&#x…

Python - 金三银四心路历程 之 数据结构与算法 刷题

目录 一.引言 二.心路历程 三.刷题经历 四.刷题历程 五.总结 一.引言 <夜深人静写算法> 是 23 年 12 月底博主打算跳槽时开始做刷题准备做的专栏&#xff0c;前后准备了大约一个月&#xff0c;刷题完毕后简单准备了项目和简历后就开始加入找工作大军了&#xff0c;最…

如何在电脑中截屏【攻略】

如何在电脑中截屏【攻略】 前言版权推荐如何在电脑中截屏电脑工具截屏键&#xff1a;PrtScQQ截屏快捷键&#xff1a;CtrlAltA微信截屏快捷键&#xff1a;AltAQQ浏览器截屏快捷键&#xff1a;CtrlShiftXEdge浏览器截屏快捷键&#xff1a;CtrlShiftS 最后 前言 2024-5-9 21:31:3…

MongoDB Atlas Vector Search与Amazon Bedrock集成已全面可用

亮点前瞻 ●MongoDB Atlas Vector Search知识库与Amazon Bedrock的最新集成&#xff0c;将极大加速生成式AI应用的开发。 ●诺和诺德利用MongoDB Atlas Vector Search与Amazon Bedrock集成&#xff0c;加速构建AI应用程序。 MongoDB&#xff08;纳斯达克股票代码&#xff1a…

scikit-learn实现单因子线性回归模型

1.是什么&#xff1a; 针对机器学习提供了数据预处理&#xff0c;分类&#xff0c;回归等常见算法的框架 2.基于scikit-learn求解线性回归的问题&#xff1a; 2.1.求解a&#xff0c;b对新数据进行预测&#xff1a; 2.2评估模型表现&#xff08;y和y’的方差MSE&#xff09;…

Linux流量分析工具 | nethogs

在应急过程中&#xff0c;经常会遇到应用访问缓慢&#xff0c;网络阻塞的情况&#xff0c;分析原因可能会想到存在恶意程序把带宽占满的可能。通过这样一个小工具可以快速定位异常占用带宽程序的路径、PID、占用流量大小或是排除由带宽占满导致服务器缓慢的猜想。 一、简介 Ne…

【ai早报-01 project】

今天和大家分享一款有趣的开源项目 01 Project。 The 01 Project is building an open-source ecosystem for AI devices. 其主旨是基于开源生态&#xff0c;构建以LLM为核心的产品&#xff0c;提供软硬件方案。 市面上类似产品: Rabbit R1, Humane Pin。 如上图所示的这款产…

保姆级零基础微调大模型(LLaMa-Factory,多卡版)

此处非常感谢https://github.com/hiyouga/LLaMA-Factory这个项目。 看到网上的教程很多都是教如何用webui来微调的,这里出一期命令行多卡微调教程~ 1. 模型准备 模型下载比较方便的方法: 1. modelscope社区(首选,速度很高,并且很多需要申请的模型都有)注意要选择代码…

MySQL加减间隔时间函数DATE_ADD和DATE_SUB的详解

目录 前言语法示例代码运用 前言 mysql中内置函数date_add 和 date_sub能对指定的时间进行增加或减少一个指定的时间间隔&#xff0c;返回的是一个日期。 语法 添加时间间隔 DATE_ADD(date,INTERVAL expr type)SELECT DATE_add(NOW(),INTERVAL -7 DAY);//获取7天前的日期 S…

编译和链接(超详细)

✅博客主页:爆打维c-CSDN博客​​​​​​ &#x1f43e; &#x1f539;分享c语言知识及代码 一、编译和链接实例 假设我们有一个名为main.c的C语言源文件&#xff0c;它包含了一个简单的Hello World程序。我们可以使用gcc编译器对该源文件进行编译&#xff0c;生成一个可执行…

初学者必知:ARM与单片机的区别

在开始前我有一些资料&#xff0c;是我根据网友给的问题精心整理了一份「ARM的资料从专业入门到高级教程」&#xff0c; 点个关注在评论区回复“888”之后私信回复“888”&#xff0c;全部无偿共享给大家&#xff01;&#xff01;&#xff01;ARM和单片机之间有许多区别&#…

锂电池恒流恒压CCCV充电模型MATLAB仿真

微❤关注“电气仔推送”获得资料&#xff08;专享优惠&#xff09; CCCV简介 CCCV充电过程是恒流充电&#xff08;CC&#xff09;和恒压充电&#xff08;CV&#xff09;的结合。在CC阶段对电池施加恒定电流&#xff0c;以获得更快的充电速度&#xff0c;此时电池电压持续升高…

python爬取sci论文等一系列网站---通用教程超详细教程

环境准备 确保安装了Python以及requests和BeautifulSoup库。 pip install requests beautifulsoup4确定爬取目标 选择一个含有SCI论文的网站&#xff0c;了解该网站的内容布局和数据结构。 &#xff08;1&#xff09;在浏览器中访问目标网站&#xff0c;右键点击页面并选择…

免费开源低代码平台种草推荐

从业20载&#xff0c;从当初的兴奋&#xff0c;到最后的麻木&#xff0c;甚至怀疑&#xff1a; 程序员是不是就是在不断的学习各种技术&#xff0c; 然后做着同样的重复劳动&#xff08;体力劳动&#xff09;&#xff0c;在各种业务系统上用各种技术做同样的增删改查。 对的&am…

每日两题 / 104. 二叉树的最大深度 102. 二叉树的层序遍历(LeetCode热题100)

104. 二叉树的最大深度 - 力扣&#xff08;LeetCode&#xff09; 递归判断&#xff0c;当前节点的最大深度为1 max(左节点的最大深度&#xff0c;右节点的最大深度) /*** Definition for a binary tree node.* struct TreeNode {* int val;* TreeNode *left;* …