个人主页:平行线也会相交💪
欢迎 点赞👍 收藏✨ 留言✉ 加关注💓本文由 平行线也会相交 原创
收录于专栏【C++之路】💌
本专栏旨在记录C++的学习路线,望对大家有所帮助🙇
希望我们一起努力、成长,共同进步。🍓
目录
- reserve
- resize
- insert
- erase
- string& erase (size_t pos = 0, size_t len = npos);
- iterator erase (iterator p);
- replace
- string& replace(size_t pos, size_t len, const string& str);
- c_str
- find
- find_first_of
reserve
reverse
:在不改变字符串内容的前提下,预留一定的内存空间。
具体来说,当我们调用 reserve(n)
函数时,字符串对象会在内部分配至少能够容纳 n 个字符的内存空间,但是并不会对字符串长度进行改变。这就可以避免对字符串多次进行扩充操作,从而提高更改字符串长度的效率。
使用 reserve 函数
并不会改变字符串对象的长度,如果需要更改字符串长度,可以使用 resize()
函数来完成,这个函数也可以指定字符串对象的长度,并自动调整内存大小。
举个例子,请看:
//这个地方不一定会开50的空间,也有可能比50还大一点,但是一定会开大于等于50的空间
int main()
{
std::string str = "Hello, World!";
std::cout << "Before reserve, capacity = " << str.capacity() << std::endl;
str.reserve(50);
std::cout << "After reserve, capacity = " << str.capacity() << std::endl;
return 0;
}
那现在我们来试一试reverse
的空间容量会不会缩回去呢?请看:
上面的实现是用vs来进行实现的,所以reverse空间并不会收缩,但是如果换Linux平台的话,可能就收缩了,所以reverse究竟收缩与否取决于平台
,甚至是取决于不同平台下的不同版本。
resize
当我们调用 resize(n) 函数
时,字符串对象会被调整为包含 n 个字符的大小。如果新的对象长度比原来对象长度要短,则被截断部分的字符会被删除。如果新的对象长度比原来对象长度要长,则被新增部分的字符将会填充为 ‘\0’ 字符。
resize()
可以接受两个参数,第一个参数表示新的字符串长度,第二个参数表示填充字符,如果忽略第二个参数,则默认填充字符为 ‘\0’。
还是来举个例子:
如果我们想填充为x
的话,我们可以这样,请看:
当n比字符串数组小的时候,会对多余的数据进行删除,请看举例:
可以看到并不会缩容。
insert
还是来看举例:
如果要使用迭代器的话,请看:
但是如果我们不想要在第一个位置开始插入呢,我们想要在任意位置进行插入的话,我们可以使用指针的用法进行指针的加减,比如 str.insert(str.begin() + 5, 5, 'b');
请看:
我们可以看到insert
确实好用,可以在任意位置进行插入,但是这样效率会非常低,因为既然insert
可以在任意位置插入元素的话就需要挪动数据,我们已经知道挪动数据的效率是非常低的,所以insert
还是少用为好。
erase
earse
:用于删除字符串中的一部分。
string& erase (size_t pos = 0, size_t len = npos);
先来看第一个函数原型(string& erase (size_t pos = 0, size_t len = npos);
),其中,pos 表示要删除的起始位置(默认从 0 开始),len 表示要删除的字符数。如果不传入参数,则默认删除整个字符串。
该函数返回一个引用,指向被删除部分的 string 对象本身。请看:
iterator erase (iterator p);
iterator erase (iterator p);
,用于从指定位置(迭代器p所指向的位置)删除一个元素,并返回指向被删除元素后面的元素的迭代器。
position
表示指向容器中要删除的元素的迭代器。
replace
string& replace(size_t pos, size_t len, const string& str);
string& replace(size_t pos, size_t len, const string& str);
:用来替换字符串中的字符或子字符串。
其中,pos
表示要替换的子字符串在源字符串中的起始位置,len
表示要替换的子字符串的长度,str
表示要替换成的目标字符串。
请看举例:
把所有
空格
替换为20%
c_str
c_str函数
返回一个指向当前string对象所包含的字符串内容的C风格
(即以’\0’结尾的字符数组)字符串的指针。
这个函数通常用于将string对象转换为C风格字符串,以便将其传递给一些C语言接口,因为这些接口可能无法处理C++的string对象。例如,在使用一些基于C的库的时候,我们可以使用c_str
函数将string对象
转换为字符数组来与这些库进行交互。
还是来举个例子来帮助大家来理解c_str
,比如我们如何用C语言中的接口来打开这个文件呢:string filename = "test.cpp";
,此时我们就需要一个C语言和C++中的一些衔接。
再比如,有一个string对象str,可以使用str.c_str()来返回一个指向C字符串的指针,请看:
find
我们先找到一个能够找到的例子,请看:
那如果我们找不到这里返回的应该是什么呢?
find函数返回一个size_t类型的位置信息,表示找到的子串的起始位置。如果没有找到指定子串,则返回一个特殊的常量std::string::npos,通常值为-1。
我们再来举个不能找到的例子,请看:
下面我们来做一个小题目:给定一个网址,将其中的协议 域名 资源名分别提取出来。请看:
int main()
{
//https://legacy.cplusplus.com/reference/string/string/
string ur1 = "https://legacy.cplusplus.com/reference/string/string/";
//协议(protocol) 域名(domain) 资源名
size_t pos1 = ur1.find("://");
string protocol;
cout << "pos1:" << pos1 << endl;
if (pos1 != string::npos)
{
protocol = ur1.substr(0, pos1);
}
cout << "protocol:" << protocol << endl;//取协议
size_t pos2 = ur1.find('/', pos1 + 3);
string domain;
string uri;
if (pos1 != string::npos)
{
domain = ur1.substr(pos1 + 3, pos2 - (pos1 + 3));
uri = ur1.substr(pos2 + 1);
}
cout << "domain:" << domain << endl;//取域名
cout << "uri:" << uri << endl;//这里可以直接取资源名
return 0;
}
find_first_of
find_first_of
函数用于在字符串中查找第一个出现指定字符集合中任何一个字符的位置。
请看举例:
//find_first_of
//Maybe next year's situation will be very different from this year's.
int main()
{
string str("Maybe next year's situation will be very different from this year's.");
size_t found = str.find_first_of("aeiou");
while (found != string::npos)
{
str[found] = '*';
found = str.find_first_of("aeiou");
}
cout << str << endl;
return 0;
}
好了,以上就是stl中string类的一些成员函数
,就到这里吧。
再见啦,友友们!!!