C++初阶——string(字符数组),跟C语言中的繁琐设计say goodbye

news2024/11/24 20:48:22

前言:在日常的程序设计中,我们会经常使用到字符串。比如一个人的身份证号,家庭住址等,只能用字符串表示。在C语言中,我们经常使用字符数组来存储字符串,但是某些场景(比如插入,删除)下操作起来很繁琐。在C++中,底层设计了一个string类,将经常使用的功能封装在其中,使用起来非常简单,便捷。
本文主要介绍string的使用方法和几个常用函数,最后再列举几个经典例题。
我们使用string时经常会用到它封装的函数,这里推荐一个网站:C++ Reference。函数忘了怎么使用时可以参考该网站。

目录

  • 一.介绍
  • 二.使用
    • 1.创建一个字符数组存储字符串hello world:
    • 2.截取部分字符串
    • 3.从键盘上输入
  • 三.常用重载运算符和函数
    • 1.+/+=
    • 2.size()
    • 3.capacity()
    • 4.reserve()
    • 5.[]运算符(遍历string)
    • 6.push_back()(尾部插入一个字符)
    • 7.append() (尾部插入一段字符串)
    • 8.insert() (头部插入)
  • 四.迭代器
    • 1.iterator 正向迭代器(重点)
    • 2.reverse_iterator 反向迭代器
    • 3.reverse函数(字符串逆置神器)
  • 五.例题
    • 1.字符串相加
    • 2.字符串最后一个单词长度

一.介绍

长话短说,不将它讲的太神秘:
string是用字符的顺序数组实现的类,用于管理字符数组。
我们平常怎么使用自定义的类,就怎么使用string。

二.使用

1.创建一个字符数组存储字符串hello world:

格式:string 对象("字符或字符串")
1.形如string str2("hello world"),实际上就是调用string类的构造函数初始化对象str2.
2.string类中有流提取流插入运算符重载,可以直接输出或者输出string类型数据。

//C语言
char str1[] = "hello world";
//C++
string str2("hello world"); //构造函数
string str3("#");  //单个字符
cout << str2 << endl; //string类中有流提取流插入运算符重载,可以直接输出或者输出string类型数据。

控制台输出如下:
在这里插入图片描述

2.截取部分字符串

string类对此也进行了设计:第一个参数为截取string对象,第二个为需要截取部分的起始下标,第三个参数为截取字符个数(单位是字节);
在这里插入图片描述

如下代码:想截取s1对象中的world给给s2,w的下标为6(第二个参数),world有5个字符(第三个参数)

int main()
{
	string s1("hello world");
	string s2(s1, 6, 5); //截取s1对象中的world给给s2
	cout << s2 << endl;
}

控制台输出如下,可以看到截取成功了:
在这里插入图片描述

3.从键盘上输入

这里就可以体现string的优点:
使用C语言,我们需要考虑给字符数组开多大的空间,而string不用我们考虑这点,我们只管输入,编译器会自动帮我们适配合适的空间。

int main()
{
	string s1; //实例化一个对象s1
	cin >> s1; // 输入
	cout << s1 << endl; //打印
	return 0;
}

如下:前两行为从键盘上输入的,后两行为打印的。
在这里插入图片描述

三.常用重载运算符和函数

string函数设计的接口,感兴趣的可以去文章开头给的网站看看。下面某些函数只给出常用的接口。

1.+/+=

单从这个题目,就能让你感受到string的魅力!

请看题目:从键盘上输入两个字符串,要求将后一个字符串拼接到前一个字符串后面,输出拼接后的前一个字符串。(字符串长度不超过50字节)
从C语言角度考虑:首先我们要开两个不小于50字节的字符数组,之后简单一点的就是使用strcat函数拼接。但是strcat函数长久不用我忘掉了呢,还要再去翻看笔记回忆。

C++string类对+运算符进行了重载,这个+的本质就是尾插

int main()
{
	string s1, s2;
	cin >> s1 >> s2;
	s1 = s1 + s2;  //s1,s2顺序不能颠倒
	//s1 += s2; //使用+=也可以
	cout << s1 << endl;
	return 0;
}

控制台输出如下:其中第一行为输入的s1,第二行为输入的s2,第三行为拼接后的s1
在这里插入图片描述

2.size()

返回string对象的有效字符长度(不包括\0),相当于C语言的strlen。

int main()
{
	string s1("hello world");
	cout << s1.size() << endl;
	return 0;
}

控制台输出如下:
在这里插入图片描述

3.capacity()

返回string对象的容量
我们知道string会自动扩容,而它当然不是一个一个字节阔的,它是按照一定倍率扩容。

int main()
{
	string s1("hello world");
	cout << "size:" << s1.size() << endl;
	cout << "capacity:" << s1.capacity() << endl;
	return 0;
}

控制台输出如下:可以看到有效字符大小为11字节,容量为15字节。
在这里插入图片描述

4.reserve()

reserve——保留(不要把它当成reverse(逆置))
功能:请求容量的变化
价值:如果确定大概需要开多大的空间,可以提前开好,减少扩容,提高效率。(扩容是有代价的,特别是异地扩容,需要拷贝旧空间的数据移到新空间)

int main()
{
	string s1("hello world");
	cout << "size:" << s1.size() << endl;
	cout << "原capacity:" << s1.capacity() << endl;
	s1.reserve(100);
	cout << "新capacity:" << s1.capacity() << endl;
	return 0;
}

控制台输出如下:
在这里插入图片描述

5.[]运算符(遍历string)

string类对[]运算符进行了重载,使得我们可以借助[]像访问数组一样访问string。对于解决一些与字符串有关的题很有帮助。

以遍历string为例:

int main()
{
	string s1("hello world");
	for (size_t i = 0; i < s1.size(); i++) //运用size()函数
	{
		cout << s1[i] << " ";  //下标访问
	}
	return 0;
}

控制台输出如下:
在这里插入图片描述

6.push_back()(尾部插入一个字符)

在string对象尾部插入一个字符

int main()
{
	string s1("hello world");
	s1.push_back('x');
	cout << s1 << endl;
	return 0;
}

控制台输出如下:
在这里插入图片描述

7.append() (尾部插入一段字符串)

形式:append(字符串/string对象)
实际上设计的有些冗余,插入的话我们直接用+=就行了,何必再使用append函数呢?

int main()
{
	string s1("hello world");
	string s2("!!!");
	s1.append("xxx");
	s1.append(s2);
	cout << s1 << endl;
	return 0;
}

控制台输出如下:
在这里插入图片描述

8.insert() (头部插入)

插入一个字符:
1.常规做法:s.insert(起始位置下标,插入个数,要插入字符)
2.迭代器做法:s.insert(s.begin(),要插入字符)

int main()
{
	string s1("hello world");
	string s2("hello world");
	string s3("hello world");
	s1.insert(1,1,'x'); // 在h后插入一个x
	s2.insert(1, 2, 'x'); // 在h后插入两个x 
	s3.insert(s3.begin(), 'x'); // 头插x 
	cout << "s1 = " << s1 << endl;  //hxello world
	cout << "s2 = " << s2 << endl;  //hxxello world
	cout << "s3 = " << s3 << endl;  //xhello world
	return 0;
}

插入一段字符串:s.insert(起始位置下标,字符串)

int main()
{
	string s1("hello world");
	s1.insert(1,"xx");
	cout << s1 << endl; //hxxello world
	return 0;
}

四.迭代器

1.iterator 正向迭代器(重点)

函数名作用(下面函数仅适用于正向迭代器!!!)
begin()返回string开头的地址
end()返回string最后一个有效字符的下一个位置的地址(一般都是\0

iterator是迭代器的意思,它封装在string类中(list,树等数据结构中都有迭代器),故而使用时要受string类域限制,要写成string::iterator形式。使用时可以将它想象成一个指针来理解。

借助迭代器遍历string:

int main()
{
	string s1("hello world");
	string::iterator str = s1.begin();
	//auto str = s1.begin(); 写成这样也可以,auto是类型指示符,可以根据begin推出正向迭代器
	while (str != s1.end())  
	{
		cout << *str << " ";
		++str;
	}
	cout << endl;
	return 0;
}

控制台输入如下:
在这里插入图片描述

在这里插入图片描述
上述代码借助begin()函数返回开始位置的迭代器,end()指向最后一个字符下一个位置(此处就是\0)。

问:可这样子不就是单纯的指针遍历吗,何必那么麻烦还使用迭代器?
答:迭代器的一个特点就是通用性,在vector,list,树等中都有迭代器。就以list举例,它是由一个一个的小结点组成的,物理空间中并不是连续的,使用结点指针++并不能找到它的下一个结点,但是像上述代码一样套上迭代器就可以遍历list。因此,迭代器遍历才是最主流的遍历方式。

2.reverse_iterator 反向迭代器

函数名作用(下面函数仅适用于反向迭代器!!!)
rbegin()返回string最后一个有效字符的下一个位置的地址(一般都是\0
rend()返回string开头的地址

顾名思义,跟正向迭代器相反,reverse_iterator是反正使用的。

借助反向迭代器倒着遍历string:

int main()
{
	string s1("hello world");
	string::reverse_iterator str = s1.rbegin();
	//auto str = s1.rbegin(); 写成这样也可以,auto是类型指示符,可以根据rbegin推出反向迭代器
	while (str != s1.rend())
	{
		cout << *str << " ";
		++str;
	}
	cout << endl;
	return 0;
}

控制台输入如下,可以看到它是倒着遍历的:
在这里插入图片描述

补:const迭代器:const_iterator const_reverse_iterator
总计共有4种迭代器。

3.reverse函数(字符串逆置神器)

传入迭代器区间: reverse(s.begin(),s.end());

int main()
{
	string s1("hello world");
	reverse(s1.begin(), s1.end()); //传入迭代器区间
	cout << s1 << endl;
	return 0;
}

控制台输出如下:
在这里插入图片描述

五.例题

1.字符串相加

点击链接

高精度,不能用整型或长整型直接相加。
运用string一位一位相加进位。

class Solution {
public:
    string s;
    string addStrings(string num1, string num2) {
        int end1 = num1.size()-1,end2 = num2.size()-1;
        int ret = 0,sum = 0;
        while(end1 >= 0 || end2 >= 0)
        {
            int n1 = end1>=0?num1[end1]-'0':0;
            int n2 = end2>=0?num2[end2]-'0':0;
            sum = n1+n2+ret;
            ret = sum/10;
            s += sum%10+'0';
            --end1;
            --end2;
        }
           if(ret == 1)
              s += '1';
        reverse(s.begin(),s.end());
        return s;
    }
};

2.字符串最后一个单词长度

1.牛客要包头文件 < string >
2.rfind()若没找到,返回无符号的-1
3.string::npos == 无符号的-1
4.注意只有一个单词的情况

#include <iostream>
#include<string>
using namespace std;
int main()
{
    string s1;
    getline(cin,s1);
    size_t eblack = s1.rfind(' '); //倒着找第一个空格,没找到返回无符号的-1
    if(eblack != string::npos)
    {
        cout << s1.size()-(1+eblack); //下标-1
    }
    else {
        cout << s1.size();
    }
    return 0;
}

文末BB:对哪里有问题的朋友,尽管在评论区留言,若哪里写的有问题,也欢迎朋友们在评论区指出,博主看到后会第一时间确定修改。最后,制作不易,如果对朋友们有帮助的话,希望能给博主点点赞和关注.
在这里插入图片描述

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

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

相关文章

在线HmacSHA256加密工具--在线获取哈希值又称摘要

具体请前往&#xff1a; 在线计算HmacSha256工具

【Unittest】Unittest接口测试框架开发-以登录模块为例

文章目录 框架结构框架目录结构封装被测试系统接口定义接口测试用例集成测试报告测试数据参数化&#xff08;一&#xff09;分析与数据构造&#xff08;二&#xff09;基于JSON实现参数化&#xff08;三&#xff09;基于数据库实现参数化 框架结构 框架结构包括&#xff1a;被…

Stable Diffusion:使用自己的数据集微调训练LoRA模型

Stable Diffusion&#xff1a;使用自己的数据集微调训练LoRA模型 前言前提条件相关介绍微调训练LoRA模型下载kohya_ss项目安装kohya_ss项目运行kohya_ss项目准备数据集生成关键词模型参数设置预训练模型设置文件夹设置训练参数设置 开始训练LoRA模型TensorBoard查看训练情况 测…

[JAVAee]Tomcat - Servlet

目录 Tomcat Servlet的工作 创建Servlet ①项目 ②依赖 ③目录 ④代码 ⑤打包 ⑥部署 ⑦验证 Servlet的运行原理 Servlet API HttpServlet 方法 处理Get/POST请求 HttpServletRequest 方法 获取请求中的信息 获取GET请求中的参数 获取POST请求中的参数…

基于YOLOv8模型和PCB电子线路板缺陷目标检测系统(PyTorch+Pyside6+YOLOv8模型)

摘要&#xff1a;基于YOLOv8模型PCB电子线路板缺陷目标检测系统可用于日常生活中检测与定位PCB线路板瑕疵&#xff0c;利用深度学习算法可实现图片、视频、摄像头等方式的目标检测&#xff0c;另外本系统还支持图片、视频等格式的结果可视化与结果导出。本系统采用YOLOv8目标检…

Dbeaver安装与报错解决方案

官网 https://dbeaver.io/ Dbeaver &#xff1a;社区版&#xff0c;开源免费。 下载 下载地址&#xff08;官网下载不了&#xff0c;在GitHub下载&#xff09;&#xff1a; https://github.com/dbeaver/dbeaver/releases 安装过程中的问题 双击安装包&#xff0c;按照提示…

第7步---MySQL的视图操作和

第7步---MySQL的视图操作 虚拟表。保存的只是视图的定义。不存放真实的数据&#xff0c;数据还是在原先的表中。 好处是方便和简化代码以及安全。 1.视图创建 数据准备 -- 创建表的测试数据 create table dept(deptno int primary key,dname varchar(20),loc varchar(20) ); …

基于Java+SpringBoot+vue前后端分离在线BLOG网站系统设计实现

基于JavaSpringBootvue前后端分离在线BLOG网站系统设计实现&#xff08;程序源码毕业论文&#xff09; 大家好&#xff0c;今天给大家介绍基于JavaSpringBootvue前后端分离在线BLOG网站系统设计与实现&#xff0c;本论文只截取部分文章重点&#xff0c;文章末尾附有本毕业设计完…

CPU缓存一致性原理

CPU缓存一致性原理 在本站的文章CPU缓存那些事儿中&#xff0c; 介绍了cpu的多级缓存的架构和cpu缓存行cache line的结构。CPU对于缓存的操作包含读和写&#xff0c;读操作在cache line中有所涉及&#xff0c;在本文中&#xff0c;将重点讨论CPU对于缓存进行写时的行为。 单核…

jmap(Memory Map for Java)Java内存映像工具

jmap&#xff08;Memory Map for Java&#xff09;Java内存映像工具 jmap&#xff08;Memory Map for Java&#xff09;命令用于生成堆转储快照&#xff08;一般称为heapdump或dump文件&#xff09; 如果不使用jmap命令&#xff0c;要想获取Java堆转储快照也还有一些比较“暴…

Linux -- 进阶 利用大文件来增加分区 自动挂载大文件

情景引入 &#xff1a; 比如&#xff0c; 你的硬盘 分了三个区&#xff0c;但是&#xff0c;现在就是要求要分第四个区&#xff0c; 你一看硬盘没有剩余空 间了&#xff0c;分不出第四个区了&#xff0c;除非你再添加 一块儿 新硬盘。 那就可以使用我们介绍的这种方法 &…

MyBatis入门配置及CURD实现

目录 一、MyBatis简介 1. 什么是 MyBatis ? 2. MyBatis的特性 3. 什么是持久层框架&#xff1f; 二、MyBatis环境配置 2.1 创建maven工程 2.2 导入相关pom依赖 2.3 导入jdbc配置文件 2.4 Mybatis相关插件安装 3.5 Mybatis-cfg.xml 核心配置 2.6 引入Log4j2日志文件…

【前缀和】算法实战

文章目录 一、算法原理1. 一维前缀和2. 二维前缀和 二、算法实战1. leetcode560 和为K的子数组2. leetcode974 和可被K整除的子数组3. leetcode525 连续数组4. leetcode1314 矩阵区域和5. leetcode724 寻找数组的中心下标6. leetcode238 除自身以外数组的乘积 三、总结 一、算法…

基于Python的高校学生成绩分析系统

随着计算机技术发展&#xff0c;计算机系统的应用已延伸到社会的各个领域&#xff0c;大量基于网络的广泛应用给生活带来了十分的便利。所以把高校成绩分析与现在网络相结合&#xff0c;利用计算机搭建高校成绩分析系统&#xff0c;实现高校成绩分析的信息化。则对于进一步提高…

gdb调试core dump

gdb调试core dump 文章目录 gdb调试core dumpgdb core dump调试步骤Segmentation faultcore dump**coredump文件的存储位置**apport手动指定存储位置 开启coredump测试readelf 查看core dump文件信息gdb查看core文件总结Reference>>>>> 欢迎关注公众号【三戒纪元…

P17~P18 电路定理 电路中难得的精彩到极致的电路理论

特勒根定理、互易定理、对偶定理比较难&#xff0c;非常重要&#xff0c;因为他们可以解决其他定理无法解决的问题。 1、特勒根定理1——个人感觉像能量守恒 特勒根定理与基尔霍夫定理齐名&#xff0c;与拓扑结构有关。都适用于任何线性非线性&#xff0c;时变的非时变的元件…

使用zoom预览出图和系统相机预览出图,画质不一样的问题分析

1、问题背景 最近在基于 Android 的平台调试一款摄像头&#xff0c;客户有反馈一个问题&#xff0c;系统自带的 Camera2 app 预览出图是正常的&#xff0c;但用 Zoom app 打开摄像头&#xff0c;出图画面存在畸变、锯齿、过曝的问题&#xff0c;现象如下图所示。 2、问题分析 …

前端基础(Web API)

目录 前言 Web API DOM 基本概念 查找元素 document.getElementById document.getElementsByClassName document.evaluate() 修改元素 添加元素 修改元素 复制元素 删除元素 Event事件 事件创建 常用的事件 监听事件 click事件 mouseover事件 事件绑定…

LTPP在线开发平台【使用教程】

LTPP在线开发平台 点击访问 LTPP在线开发平台 LTPP&#xff08;Learning teaching practice platform&#xff09;在线开发平台是一个编程学习网站&#xff0c;该网站集文章学习、短视频、在线直播、代码训练、在线问答、在线聊天和在线商店于一体&#xff0c;专注于提升用户编…

使用SpringBoot+SpringMVC+Mybatis+WebSocket实现云聊天项目

云聊天 1. 项目介绍 本项目是仿照微信实现网页版聊天程序&#xff0c;用户注册登录后可与在线好友实时聊天&#xff0c;下线好友上线后可以查看到好友发送的消息&#xff1b;用户可以在搜索框搜索用户添加好友&#xff1b;用户还可以查看好友申请列表&#xff0c;选择是否同意…