C++ STL(二):string容器


1 string基本概念

string和char *的区别
string:C++风格的字符串;本质是。string类内部封装char*成员属性,是char*型容器,底层维护C语言的字符串。
char *:C风格的字符串;本质是指针

特点
(1)string类的内部封装了许多用于操作字符串成员方法,例如:查找find、拷贝copy、删除delete、替换replace、插入insert等。
(2)string类管理char*的内存分配时,无需担心复制越界、取值越界、内存释放(析构调用)等,由string类的内部负责管理。


2 string构造函数

构造函数原型
(1)string();:默认无参构造函数,创建一个空字符串,如string str;
(2)string(const char* s); :有参构造函数,使用C语言字符串s初始化一个C++风格字符串
(3)string(const string& str);:拷贝构造函数,使用已有string对象初始化新的string对象。
(4)string(int n, char c);:有参构造函数,使用n个字符c初始化一个C++风格字符串

注:string的多种构造方式之间无可比性,灵活使用即可。

示例:string的构造函数

#include<iostream>
#include<string>
using namespace std;

int main() {
    
    
	/* 默认无参构造 */
	string str1;
	cout << "str1 = " << str1 << endl;	//(空字符串)

	/* 有参构造:使用C风格的const char*字符串初始化 */
	const char* cstr = "hello cpp";
	string str2(cstr);
	cout << "str2 = " << str2 << endl;	//hello cpp

	/* 拷贝构造 */
	string str3(str2);
	cout << "str3 = " << str3 << endl;	//hello cpp

	/* 多个字符拼接 */
	string str4(5, 'h');
	cout << "str4 = " << str4 << endl;	//hhhhh

	return 0;
}

3 字符串长度【size()、length()、strlen()】

(1)const char*类型的字符串长度
使用函数strlen(const char* s)获取字符串长度不包含'\0'结束符)。
函数原型unsigned int strlen(const char *pStr);

注1:运算符sizeof("xxx")计算的是占用的内存空间大小包含'\0'结束符),而不是字符串长度。
注2:单个英文字符的长度为1;单个中文字符的长度为2

//const char*字符串的长度-英文字符占1个字符长度
cout << strlen("world") << endl;		//字符串长度:5(未计算'\0')
cout << sizeof("world") << endl;		//内存大小:6字节(计算'\0')
									
//const char*字符串的长度-中文字符占2个字符长度
cout << strlen("世界和中国") << endl;	//字符串长度:10(未计算'\0')
cout << sizeof("世界和中国") << endl;	//内存大小:11字节(计算'\0')

(2)string类型的字符串长度
①使用成员函数size()length()获取字符串长度不包含'\0'结束符)。
string类型对象可调用成员函数c_str()转换为const char*类型,再使用strlen(const char* s)获取字符串长度,即strlen(str.c_str())
函数声明const char* string::c_str() const;

//string字符串的长度-英文字符占1个字符长度
string str1 = "hello";
cout << "str1的长度:" << str1.length() << endl;			//5
cout << "str1的长度:" << str1.size() << endl;			//5
cout << "str1的长度:" << strlen(str1.c_str()) << endl;	//5

//string字符串的长度-中文字符占2个字符长度
string str2 = "世界和中国";
cout << "str2的长度:" << str2.length() << endl;			//10
cout << "str2的长度:" << str2.size() << endl;			//10
cout << "str2的长度:" << strlen(str2.c_str()) << endl;	//10

4 string赋值操作【operator=、assign()】

作用:通过重载赋值运算符operator=成员函数assign(),对string字符串进行赋值。

注:string的赋值操作,重载赋值运算符operator=的方式更常用

赋值操作的函数原型
(1)string& operator=(const char* s);:使用const char*类型的字符串,对当前字符串赋值。
(2)string& operator=(const string &s); :使用string类型的字符串s,对当前字符串赋值。
(3)string& operator=(char c);:使用单个字符,对当前字符串赋值。


(4)string& assign(const char *s);:使用const char*类型的字符串,对当前字符串赋值。
(5)string& assign(const char *s, int n);:使用const char*类型的字符串s的前n个字符(子串),对当前字符串赋值。
(6)string& assign(const string &s);:使用string类型的字符串,对当前字符串赋值。
(7)string& assign(int n, char c);:使用n个字符c,对当前字符串赋值。

示例:string的赋值操作

#include<iostream>
#include<string>
using namespace std;

int main() {
    
    
	/* 重载赋值运算符operator=赋值 */
	//(1)string& operator=(const char* s); :使用const char* 类型的字符串,对当前字符串赋值。
	string str1;
	str1 = "hello";
	cout << "str1 = " << str1 << endl;	//hello

	//(2)string& operator=(const string& s); :使用string类型的字符串s,对当前字符串赋值。
	string str2;
	str2 = str1;
	cout << "str2 = " << str2 << endl;	//hello

	//(3)string& operator=(char c); :使用单个字符,对当前字符串赋值。
	string str3;
	str3 = 'a';
	cout << "str3 = " << str3 << endl;	//a

	//(4)string& assign(const char* s); :使用const char* 类型的字符串,对当前字符串赋值。
	string str4;
	str4.assign("world");
	cout << "str4 = " << str4 << endl;	//world

	//(5)string& assign(const char* s, int n); :使用const char* 类型的字符串s的前n个字符(子串),对当前字符串赋值。
	string str5;
	str5.assign("world", 2);
	cout << "str5 = " << str5 << endl;	//wo
	
	//(6)string& assign(const string & s); :使用string类型的字符串,对当前字符串赋值。
	string str6;
	str6.assign(str5);
	cout << "str6 = " << str6 << endl;	//wo
	
	//(7)string& assign(int n, char c); :使用n个字符c,对当前字符串赋值。
	string str7;
	str7.assign(5, 'h');
	cout << "str7 = " << str7 << endl;	//hhhhh

	return 0;
}

5 string字符串拼接【operator+=、append()】

作用:通过重载加法赋值运算符operator+=成员函数append(),实现在源字符串的末尾拼接目标字符串(尾部追加)。

字符串拼接操作的函数原型
(1)string& operator+=(const char* str);:将const char*类型的字符串,拼接至原字符串结尾。
(2)string& operator+=(const char c);:将单个字符,拼接至原字符串结尾。
(3)string& operator+=(const string& str);:将string类型的字符串,拼接至原字符串结尾。


(4)string& append(const char *s);:将const char*类型的字符串,拼接至原字符串结尾。
(5)string& append(const char *s, int n);:将const char*类型的字符串s的前n个字符,拼接至原字符串结尾。
(6)string& append(const string &s);:将string类型的字符串,拼接至原字符串结尾。
(7)string& append(const string &s, int pos, int n);:将string类型的字符串s中自索引位置pos起的n个字符(长度为n子串),拼接至原字符串结尾。

注:成员函数append(const string &s, int pos, int n);截取的字符串,包含索引位置pos本身的字符

示例:string的字符串拼接操作

#include<iostream>
#include<string>
using namespace std;

/* 字符串拼接 */
int main() {
    
    
	//(1)string& operator+=(const char* str); 
	//将const char* 类型的字符串,拼接至原字符串结尾。
	string str1 = "我";
	str1 += "爱学习";
	cout << "str1 = " << str1 << endl;	//我爱学习

	//(2)string& operator+=(const char c); 
	//将单个字符,拼接至原字符串结尾。
	str1 += ':';
	cout << "str1 = " << str1 << endl;	//我爱学习:

	//(3)string& operator+=(const string & str); 
	//将string类型的字符串,拼接至原字符串结尾。
	string str2 = "C++";
	str1 += str2;
	cout << "str1 = " << str1 << endl;	//我爱学习:C++

	//(4)string& append(const char* s); 
	//将const char* 类型的字符串,拼接至原字符串结尾。
	str1.append("/Python");
	cout << "str1 = " << str1 << endl;	//我爱学习:C++/Python

	//(5)string& append(const char* s, int n);
	//将const char* 类型的字符串s的前n个字符,拼接至原字符串结尾。
	str1.append("/JavaWeb", 5);
	cout << "str1 = " << str1 << endl;	//我爱学习:C++/Python/Java

	//(6)string& append(const string & s); 
	//将string类型的字符串,拼接至原字符串结尾。
	string str3 = "/MySQL";
	str1.append(str3);
	cout << "str1 = " << str1 << endl;	//我爱学习:C++/Python/Java/MySQL

	//(7)string& append(const string & s, int pos, int n);
	//将string类型的字符串s中自索引位置pos起的n个字符(长度为n的子串),拼接至原字符串结尾。
	string str4 = "Windows/Linux";
	str1.append(str4, 7, 6);
	cout << "str1 = " << str1 << endl;	//我爱学习:C++/Python/Java/MySQL/Linux

	return 0;
}

6 string查找【find()、rfind()】和替换【replace()】

(1)查找:通过成员函数find()rfind(),查找指定字符串是否存在。

find()rfind()区别find()从左往右查找;rfind()从右往左查找。

函数原型:
int find(const string& str, int pos = 0) const;【从左往右查找,第一次出现位置】
源字符串的指定索引位置pos(默认为0)起,查找string类型的目标字符串str第一次出现的索引位置。查找到,则返回匹配处第1个字符的索引位置;未查找到,则返回-1

int find(const char* s, int pos = 0) const;【从左往右查找,第一次出现位置】
源字符串的指定索引位置pos(默认为0)起,查找const char*类型的目标字符串s第一次出现的索引位置。查找到,则返回匹配处第1个字符的索引位置;未查找到,则返回-1

int find(const char* s, int pos, int n) const;【从左往右查找,第一次出现位置】
源字符串的指定索引位置pos起,查找const char*类型的目标字符串sn个字符第一次出现的索引位置。查找到,则返回匹配处第1个字符的索引位置;未查找到,则返回-1

int find(const char c, int pos = 0) const;【从左往右查找,第一次出现位置】
源字符串的指定索引位置pos(默认为0)起,查找目标字符c第一次出现的索引位置。查找到,则返回匹配处第1个字符的索引位置;未查找到,则返回-1

int rfind(const string& str, int pos = npos) const; 【从右往左查找,第一次出现位置】
源字符串的指定索引位置pos(默认为npos,即-1)起,查找string类型的目标字符串str最后一次出现的索引位置。查找到,则返回匹配处第1个字符的索引位置;未查找到,则返回-1

注1:npos是string类的静态常量,表示字符串中不存在的位置,即结束位置,通常表示为-1
定义static const size_type npos = -1;
注2:判断源字符串src是否包含目标字符串dest的方法:
if (src.find(dest) != string::npos){...}

int rfind(const char* s, int pos = npos) const; 【从右往左查找,第一次出现位置】
源字符串的指定索引位置npos(默认为npos,即-1)起,查找const char*类型的目标字符串s最后一次出现的索引位置。查找到,则返回匹配处第1个字符的索引位置;未查找到,则返回-1

int rfind(const char* s, int pos, int n) const;【从右往左查找,第一次出现位置】
源字符串的指定索引位置pos起,查找const char*类型的目标字符串sn个字符最后一次出现的索引位置。查找到,则返回匹配处第1个字符的索引位置;未查找到,则返回-1

int rfind(const char c, int pos = 0) const; 【从右往左查找,第一次出现位置】
源字符串的指定索引位置pos(默认为0)起,查找目标字符c最后一次出现的索引位置。查找到,则返回匹配处第1个字符的索引位置;未查找到,则返回-1

示例:字符串查找

#include<iostream>
#include<string>
using namespace std;

/* 字符串查找 */
void func() {
    
    
	string str1 = "abcdefgbc";
	string str2 = "bc";

	//find():从左往右查找,第1次出现位置
	int pos1 = str1.find(str2);
	if (pos1 != -1) {
    
    
		cout << "str1包含str2" << endl;
		cout << "第一次出现的索引位置为:" << pos1 << endl;		//1
	}
	else {
    
    
		cout << "str1不包含str2" << endl;
	}

	//rfind():从右往左查找,第1次出现位置(即从左往右查找时的【最后1次】出现位置)
	int pos2 = str1.rfind(str2);
	if (pos2 != -1) {
    
    
		cout << "str1包含str2" << endl;
		cout << "最后一次出现的索引位置为:" << pos2 << endl;		//7
	}
	else {
    
    
		cout << "str1不包含str2" << endl;
	}
}

(2)替换:在指定位置替换字符串。
函数原型:
string& replace(int pos, int n, const string& str);
源字符串指定索引位置pos起的连续n个字符,替换为string类型的整个目标字符串str
string& replace(int pos, int n, const char* s);
源字符串指定索引位置pos起的连续n个字符,替换为const char*类型的整个目标字符串s

示例:字符串替换

#include<iostream>
#include<string>
using namespace std;

/* 字符串替换 */
void func2() {
    
    
	string str1 = "abcdefg";
	string str2 = "****";

	//replace():将源字符串指定索引位置pos起的连续n个字符,替换为整个目标字符串
	str1.replace(1, 2, str2);	//将str1的"bc"等2个字符,替换为整个str2
	cout << "替换后的str1 = " << str1 << endl;	//a****defg
}

7 string字符串比较【compare()】

作用:通过成员函数compare()比较两个字符串。主要用于判断两个字符串是否相等,即if(s1.compare(s2) == 0)

比较方式:逐个比较每个字符的ASCII码:
①相等时,继续比较后一个字符,直至完成所有字符的比较,全部相等则返回0
②不等时,大于则返回1;小于则返回-1

函数原型
(1)int compare(const string &s) const;:将源字符串与string类型的字符串进行比较。
(2)int compare(const char *s) const;:将源字符串与const char*类型的字符串进行比较。

示例:字符串比较

#include<iostream>
#include<string>
using namespace std;

int main() {
    
    
	string str1 = "abc";
	string str2 = "acb";
	
	if (str1.compare(str2) == 0) {
    
    
		cout << "str1 等于 str2" << endl;
	}
	else if(str1.compare(str2) < 0) {
    
    
		cout << "str1 小于 str2" << endl;	//str1 小于 str2
	}
	else if (str1.compare(str2) > 0) {
    
    
		cout << "str1 大于 str2" << endl;
	}

	return 0;
}

8 string字符存取【operator[]、at()】

作用:通过重载赋值运算符operator[]成员函数at(int index),对字符串的单个字符进行(作为右值)或(作为左值)。

注:string类型字符串的底层实际为字符数组,可通过索引访问字符数组的字符元素。

字符存取的2种方式
(1)char& operator[](int index);:重载运算符[],读写指定索引位置index的字符
(2)char& at(int index);:成员函数,读写指定索引位置index的字符

示例:

#include<iostream>
#include<string>
using namespace std;

int main() {
    
    
	/* 重载运算符[]读写字符 */
	string str1 = "abcd";
	cout << "修改前:str1 = " << str1 << endl;		//abcd
	//读取字符
	cout << "str1[1] = " << str1[1] << endl;		//b
	//写入字符
	str1[1] = 'a';
	cout << "修改后:str1 = " << str1 << endl;		//aacd


	/* 成员函数at()读写字符 */
	string str2 = "abcd";
	cout << "修改前:str2 = " << str2 << endl;		//abcd
	//读取字符
	cout << "str2.at(1) = " << str2.at(1) << endl;	//b
	//写入字符
	str2.at(1) = 'a';
	cout << "修改后:str1 = " << str2 << endl;		//aacd

	return 0;
}

9 string插入【insert()】和删除【erase()】

(1)字符串插入:使用成员函数insert(..)在原字符串中插入字符串或字符

函数原型
string& insert(int pos, const char* s);:在原字符串指定索引位置pos插入const char*类型的字符串。
string& insert(int pos, const string& str);:在原字符串指定索引位置pos插入string类型的字符串。
string& insert(int pos, int n, char c);:在原字符串指定索引位置pos插入n个字符。


(2)字符串删除:使用成员函数erase(..)在原字符串中删除若干个连续字符

函数原型
string& erase(int pos, int n = npos);:从原字符串的指定索引位置pos开始,连续删除n个字符。

示例:字符串的插入与删除

#include<iostream>
#include<string>
using namespace std;

int main() {
    
    
	//insert():在原字符串指定索引位置pos前,插入字符或字符串
	string str = "abcd";
	str.insert(1, "***"); //在字符b前(索引位置1)插入***
	cout << "str = " << str << endl;	//a***bcd

	//erase():从原字符串的指定索引位置pos开始,连续删除n个字符
	str.erase(1, 3);	//从索引位置1开始,连续删除3个字符
	cout << "str = " << str << endl;	//abcd

	return 0;
}

10 string获取子串【substr()】

作用:通过成员函数substr(...),从原字符串中获取子字符串

函数原型
string substr(int pos = 0, int n = npos) const;
从原字符串的指定索引位置pos开始,截取连续n个字符作为子字符串并返回。

示例:截取子字符串

#include<iostream>
#include<string>
using namespace std;

int main() {
    
    
	string str = "helloworld";
	//从索引位置5开始截取5个字符并返回子字符串
	string newStr = str.substr(5, 5);
	cout << "newStr = " << newStr << endl;	//world


	/* 实际应用场景 */
	string email = "[email protected]";
	//获取@的索引位置(@前共有pos个字符)
	int pos = email.find("@");
	//从原字符串索引位置0,截取pos个字符
	string username = email.substr(0, pos);
	cout << "username = " << username << endl;	//NewsomTech

	return 0;
}

猜你喜欢

转载自blog.csdn.net/newson92/article/details/113930652
今日推荐