C++ string类-2

news2024/11/28 5:49:20

at

at 函数是在C++还没有支持运算符重载的时候提供的。

 他可以像 [] 重载运算符一样,找到某个位置的字符:
 

	string s1("hello world");
	s1.at(0) = 'x';
	cout << s1 << endl;

输出:

 [] 重载运算符和 at()的区别就是,在范围处理上不同,如果 访问越界,[] 采用的是断言的方式进行处理的;而 at()采用的是抛出异常。

 抛出异常:

 断言处理:

 那么异常就可以捕获异常,然后对这个异常进行处理,程序可以继续运行;但是断言程序就不能继续执行了。

string类对象的修改操作

函数名称功能说明
push_back在字符串后尾插字符c
append在字符串后追加一个字符串
operator+= (重点)在字符串后追加字符串str
c_str(重点)返回C格式字符串
find + npos(重点)从字符串pos位置开始往后找字符c,返回该字符在字符串中的位置
rfind从字符串pos位置开始往前找字符c,返回该字符在字符串中的位置
substr在str中从pos位置开始,截取n个字符,然后将其返回

 += 重载运算符函数,就是在这个字符串之后再追加字符,或者是字符串。

 append()也是在字符串后面追加字符或者是字符串,只不过这个函数有多个接口:

 assign()是在给这个字符串赋值,也就是说,会覆盖掉之前在字符串当中存储的字符串或者字符,从0开始依次覆盖了:

 insert()支持在某下标位置插入字符或者字符串:

 insert()的效率不是很好,所以偶尔用是可以的,频繁用有效率的问题。

 erase()函数可以指定个数,指定位置 删除字符串当中的字符:

 上述给的 1 这个位置的参数就是 要删除的个数,这个位置的参数是有缺省值的,如果我们不给这个参数,那么就默认把这个位置后面的字符删光。

如果我们给的个数,超过了这个字符串的结尾,那么他也不会报错,会把后面的都删光,能删多少删多少。

上述的 erase()也是尽量少用,他也是有效率的问题。

 replace()在某一个区间当中,用传入的字符串替换到原字符串当中:

 c_str() 把这个string类的对象当中的字符串以c形式的方式返回:
 

	string s1("hello world");
	
	string filename = "text.txt";
	FILE* font = fopen(filename.c_str(), "r");

find()查找函数:

 他支持从 pos 位置开始寻找这个字符串或者是字符,这个pos位置是有缺省参数的,不传入pos的话 默认从 0 位置开始找。如果找到了,就返回第一个符合要求的,首字符下标,如果没有找到就返回 npos (-1)

比如下例子,我们要去把网址的 协议,域名,资源名切分出来:

	string url = "https://legacy.cplusplus.com/reference/string/string/find/";
	size_t pos1 = url.find("://");  // "://" 字符串之前的就是协议,其中 find 函数找到的是 ':' 这个字符的下标
	string protocaol;  // 存储域名的string类型的对象

	if (pos1 != string::npos) // find 函数如果寻找失败,返回 npos
	{
		protocaol = url.substr(0, pos1); // 把协议字符串 赋值给 protocaol
	}
	cout << protocaol << endl;

	size_t pos2 = url.find("/", pos1 + 3);
	string domain;
	string uri;

	if (pos2 != string::npos)
	{
		domain = url.substr(pos1 + 3, pos2 - (pos1 + 3));
	}
	cout << domain << endl;

	uri = url.substr(pos2 + 1);
	cout << uri << endl;

输出:

 rfind()函数,这个函数的功能和 find ()的功能完全是类似的,只不过find()是从前往后找,而find()是从后往前找。

 find_first_of()函数:

 传入一个字符串,或者是一个字符,从pos位置开始寻找(pos 缺省值 = 0)和传入的字符或者是字符字符串当中的任意一个字符相等的字符(第一个),找到之后返回这个字符的下标,如下在文档中给出的例子:

要求是把 字符串当中 "a" "e" "i" "o" "u" 的字符,全部改为 "*" :

std::string str ("Please, replace the vowels in this sentence by asterisks.");
  std::size_t found = str.find_first_of("aeiou");
  while (found!=std::string::npos)
  {
    str[found]='*';
    found=str.find_first_of("aeiou",found+1);
  }

  std::cout << str << '\n';

输出:

Pl**s*, r*pl*c* th* v*w*ls *n th*s s*nt*nc* by *st*r*sks.

上述是从前往后找的函数,还有一个函数和上述函数的功能是一样的,find_last_of()函数。

  当然,还有查找 不是传入的 字符串和 字符的函数:find_first_not_of 和 find_last_not_of ;

注意:

  • 在string尾部追加字符时,s.push_back(c) / s.append(1, c) / s += 'c'三种的实现方式差不多,一般情况下string类的+=操作用的比较多,+=操作不仅可以连接单个字符,还可以连接字符串。
  • 对string操作时,如果能够大概预估到放多少字符,可以先通过reserve把空间预留好。

 string类非成员函数

函数功能说明
operator+尽量少用,因为传值返回,导致深拷贝效率低
operator>> (重点)输入运算符重载
operator<< (重点)输出运算符重载
getline (重点)获取一行字符串
relational operators (重点)大小比较

 字符串比较的重载运算符函数:

relational operators

 上述就是对应的接口,其实上述实现的接口,有限冗余,上述一个 重载运算符函数 重载了三个形参不同的函数,分别是 字符串类型 和 string 类 参数类型 变化,其实不用实现这么多,因为 如果是 string& 参数 传入 char* 类型的参数的时候,char* 在传参的时候可以隐式类型转换 为 string& 。

getline()函数和 C当中的 gets 有点像,我们在C++当中使用的 cin 输入流,和 C 当中的scanf()函数一样,当读到 空格 '\n'就会结束读入,那么我们上述cin 就不能读取字符串,所以我们就是用 getline ()来读入字符串。

例子,返回一个字符串当中,最后一个单词的 长度:

	string str;
	getline(cin, str);  // 读取字符串
	size_t pos = str.rfind(' ');
	if (pos != string::npos)
	{
		cout << str.size() - (pos + 1) << endl;
	}
	else
	{
		cout << str.size() << endl;
	}

getline 只 遇到 '\n' 才结束。

to_string  和  stoi

 

 to_string 可以把 内置类型 转换成string类型,这个函数返回的就是 string类型:
 

	string s1 = to_string(1234);
	string s2 = to_string(1.1);

	cout << s1 << endl;  //1234
	cout << s2 << endl; //1.100000

 如果是在C当中我们使用的是 itoa()函数把 int 类型转换成 字符串类型,但是这个函数不好用在于,接收的字符串类型,需要我们手动开空间。

 

如果是在 C 当中我们使用的是 atoi()来把 字符串类型转换成 int 类型:

 wstring , u16string ,u32string

 其实string是一个模板 typedef 出来的string。只不过这里面传入的是 char 类型:

 其实本源的类其实是 basic_string 这个类型,所以我们看到 关于string类的报错的时候,会看到     basic_string 字样。

 之所以这样做是因为,还有其他的string类型wstring , u16string ,u32string。

上述的本源也都是 basic_string。

上述三种类型其实不经常用,之所以把他区分开来是因为编码问题。

 我们现在经常使用的 编码格式 是 ascll 表的,就是 底层存储的值,对应的映射关系表。在计算机当中存储的值是二进制的,比如在 ascll 当中,一共就 200 多个,那么 8 个bite 位就可以存储了。存储的不同的二进制的值就代表着不同的字符,比如 0110 0000 对应的十进制是 97,那么这个二进制代表的就是 a 这个字符。

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

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

相关文章

GIT常见报错以及解决方法

GIT常见报错以及解决方法 Changes not staged for commit问题复现原理解决 warning: adding embedded git repository问题复现原理解决 error: src refspec master does not match any问题复现 Changes not staged for commit问题复现&#xff1a;解决 Changes not staged for …

软考A计划-电子商务设计师-电子商务基础知识

点击跳转专栏>Unity3D特效百例点击跳转专栏>案例项目实战源码点击跳转专栏>游戏脚本-辅助自动化点击跳转专栏>Android控件全解手册点击跳转专栏>Scratch编程案例 &#x1f449;关于作者 专注于Android/Unity和各种游戏开发技巧&#xff0c;以及各种资源分享&am…

chatgpt赋能python:Python为什么成为不可或缺的编程语言?

Python为什么成为不可或缺的编程语言&#xff1f; Python语言在过去的十年间&#xff0c;已经成为编程领域中不可或缺的一种语言。Python语言是一种高级、通用、面向对象语言&#xff0c;并且在数据科学、机器学习、网站开发等众多领域中广泛应用。本文将探讨为什么Python成为…

保护密码安全:ADSelfService Plus的重要性与优势

引言&#xff1a; 在当今数字化时代&#xff0c;密码安全对于个人和组织而言变得愈发重要。随着互联网的普及和数据泄露事件的频发&#xff0c;传统的用户名和密码已经不再足够保护我们的个人和机密信息。为了解决这个问题&#xff0c;许多组织开始采用密码管理工具&#xff0…

Fourier分析入门——第13章——信号分析

目录 第13章 信号分析 13.1 引言 13.2 加窗(windowing) 13.3 用一系列窗口采样(Sampling with an array of windows) 13.4 混叠现象(Aliasing) 13.5 通过插值重建(Reconstruction by interpolation) 13.6 非点采样(Non-point sampling) 13.7 覆盖系数规则(The coverage …

Yolov8轻量级:VanillaNet一种新视觉Backbone,极简且强大!华为诺亚2023

简到极致、浅到极致!深度为6的网络即可取得76.36%@ImageNet的精度,深度为13的VanillaNet甚至取得了83.1%的惊人性能。 1.VanillaNet 论文:https://arxiv.org/pdf/2305.12972.pdf 来自华为诺亚、悉尼大学的研究者们提出了一种极简的神经网络模型 VanillaNet,以极简主义的设…

第十三篇、基于Arduino uno,获取薄膜压力传感器的值——结果导向

0、结果 说明&#xff1a;先来看看串口调试助手显示的结果&#xff0c;第一个值是上电后检测到的平均压力值&#xff0c;第二个值是实时的压力值&#xff0c;第三个值是平均压力值和实时压力值的差值。如果是你想要的&#xff0c;可以接着往下看。 1、外观 说明&#xff1a;…

windows上简单部署flink

Windows上部署flink1.17 flink的下载链接 进入页面后下滑找到Apache Flink&#xff0c;然后找到对应版本&#xff0c;之后点击Binaries 找到xxx-bin-scala-xxx.tgz文件下载 下载完成后直接本地解压 解压后进入bin目录新增两个.bat文件&#xff08;直接复制下面内容<注意命名…

扩展dlink-connector-phoenix使其phoenix-5.0.0支持flink1.16

感慨&#xff1a;玩大数据java必须要精通,不然遇到眼花缭乱的框架以及插件拓展的时候就会一下子傻眼了。各种框架之间版本不同有现成的插件或者方案到还可以但是没有就需要自己扩展。目前我使用的是CDH6.3.2&#xff0c;flink使用的是1.6&#xff0c;Phoenix版本的是5.0.0这有在…

数据结构入门7-1(查找)

目录 注 查找的基本概念 线性表的查找 顺序查找 折半查找 分块查找 树表的查找 二叉排序树 平衡二叉树 平衡二叉树的定义 平衡二叉树的平衡调整方式 平衡二叉树的实现 B-树 B-树的定义 B-树的示意性实现 B树 注 本笔记参考&#xff1a;《数据结构&#xff08;C…

【04】数据结构与算法基础-类C语言有关操作补充 | 数组的静态、动态定义 | C、C++中内存分配 | C++中的参数传递方式-指针、数组、引用

目录 1.元素类型说明1.1顺序表类型定义1.2数组定义1.3C语言的内存动态分配1.4C的动态存储分配1.4.1创建内存1.4.2释放内存 1.5C中的参数传递1.5.1传值方式1.5.2传地址方式-指针变量1.5.3传地址方式-数组名1.5.4传地址方式-引用类型 1.元素类型说明 1.1顺序表类型定义 typedef…

HDFS 的健壮性体现在哪里?

前言 本文隶属于专栏《大数据技术体系》&#xff0c;该专栏为笔者原创&#xff0c;引用请注明来源&#xff0c;不足和错误之处请在评论区帮忙指出&#xff0c;谢谢&#xff01; 本专栏目录结构和参考文献请见大数据技术体系 正文 HDFS 的主要目标就是即使在出错的情况下也要保…

Linux进程间通信(消息队列)

可以用命令“ipcs”查看三种 IPC&#xff0c;“ipcrm”删除 IPC 对象。在 i.MX6ULL 终结者开发板终端输入“ipcs” 查看系统中存在的 IPC 信息&#xff1a; 这些 IPC 对象存在于内核空间&#xff0c;应用层使用 IPC 通信的步骤为&#xff1a; 1. 获取 key 值&#xff0c;内核…

【网络】交换机的原理和配置方法

目录 &#x1f341;交换机工作原理 &#x1f341;交换机接口的双工模式 &#x1f341;交换机命令行模式 &#x1f341;交换机常见命令 &#x1f9e7;帮助命令 &#x1f9e7;常用命令介绍 &#x1f341;交换机的基本配置 &#x1f9e7;配置接口的双工模式及速率 &#x1f990;博…

数据库误删恢复

说明 经常听说删库跑路这真的不只是一句玩笑话&#xff0c;若不小心删除了数据库&#xff0c;事情很严重。你一个不小心可能会给公司删没。建议研发不要直连生成环境&#xff0c;一般的话都会分配账号权限&#xff0c;生产环境的账号尽量是只读&#xff0c;以防你一个不经意给库…

java快速结束嵌套循环

java快速结束嵌套循环 快速结束for循环 out:for (int i 0; i < 5; i) {in:for (int j 0; j < 5; j) {if (j 2) {break out;}System.out.println("i " i " j " j);}}解释 将外层for循环起别名 o u t \color{red}{out} out,将内层for循环起别名…

Java NIO-非阻塞I/O(一)

文章目录 1. 简介2. 一个示例服务器3. 缓冲区4. 创建缓冲区5. 填充与排空6. 批量方法7. 数据转换8. 视图缓冲区9. 压缩缓冲区10. 复制缓冲区11. 分片缓冲区 1. 简介 与CPU和内存相比&#xff0c;甚至和磁盘相比&#xff0c;网络都很慢&#xff0c;但要允许CPU速度高于网络&…

YOLOV8最强操作教程.

YoloV8详细训练教程. 相信各位都知道yolov8发布了&#xff0c;也是U神大作&#xff0c;而且V8还会出论文喔&#xff01; 2023.1.17 更新 yolov8-grad-cam热力图可视化链接 2023.1.20 更新 YOLOV8改进-添加EIoU,SIoU,AlphaIoU,FocalEIoU 链接 2023.1.30 更新 如果你需要修改或者…

Vector Scope

下面以PicoScope 6403E-034为例说明 1.Scope 硬件结构介绍 前面板&#xff1a; 最多支持捕获2路CAN/CANFD/FlexRay总线&#xff0c;或者4路LIN总线 后面板&#xff1a; Scope Bus Probe 300 Mhz 2.Option Scope使用条件 前提条件1&#xff1a;购买CANoe/CANalyzer Option Sc…

03-SpringBoot3JDK9~17新特性

1、JDK9新特性---jshell交互式工具 前提是已经配置好了Jdk的环境变量。 2、JDK9新特性---模块化开发 需求&#xff1a; testA可以被模块A调用&#xff0c;testB可能是内部工具类&#xff0c;不想被模块A调用&#xff0c;又不能设置成private。 这时候我们就会用到模块化开发。…