C++:STL----string相关使用接口

string相关接口

头文件#include <string>

一、关于编码集

void test_string1()
{
	char str1[] = "吃饭";
	cout << str1 << endl;

	char str2[5];
	str2[0] = -77;
	str2[1] = -43;
	str2[2] = -73;
	str2[3] = -70;
	str2[4] = '\0';
	cout << str2 << endl;
}

str2输出为“痴泛”,说明底层的汉字字符都是通过编码集控制的。
在这里插入图片描述

二、关于构造函数

构造函数有很多,我们经常用的就是直接用字符串构造,拷贝构造,赋值操作符。还有一些构造函数可以确定从某个位置开始进行拷贝构造,具体看下方代码中的相关接口。

void test_string2()
{
	string s1("hello");//构造
	string s2(s1);//拷贝构造
	string s3("world");
	s1 = s3;//赋值
	cout << s1 << endl;
	cout << s2 << endl;
	cout << s3 << endl;

	string s4(s3, 3);//从对象的第三位开始取,直到\0
	cout << s4 << endl;

	string s5("world", 3);//取该字符串的前三位
	cout << s5 << endl;

	string s6(s3, 1, 3);//从对象的第一位开始取,取三位
	cout << s6 << endl;

	string s7("world", 1, 3);//从该字符串的第一位开始取,取三位
	cout << s7 << endl;
}

在这里插入图片描述

三、size/capacity

size: 返回的是当前string对象的大小(length和size的作用相同,但是我们经常用size)
capacity: 返回的是容量的大小
push_back:尾插一个字符

void test_string3()
{
	string s1("hello");
	s1.push_back(' ');
	s1.push_back('w');
	s1.push_back('o');
	s1.push_back('r');
	s1.push_back('l');
	s1.push_back('d');
	cout << s1.size() << endl;
	cout << s1.length() << endl;
	cout << s1.capacity() << endl;//最开始capacity容量为15
	//持续插入就会增容
	s1.push_back('d');
	s1.push_back('d');
	s1.push_back('d');
	s1.push_back('d');
	s1.push_back('d');
	cout << s1.size() << endl;
	cout << s1.length() << endl;
	cout << s1.capacity() << endl;//空间不够,增容
}

如果我们想观测到增容是怎么增的,我们可以写这么一段代码测验一下。
容量最开始一般是15,第一次增容是增2倍,之后增容基本是增1.5倍

void test_string4()
{
	//string的增容过程:第一次2倍,之后是1.5倍增容
	string s;
	size_t sz = 0;
	cout << "making s grow:\n";
	for (int i = 0; i < 100; ++i)
	{
		s += 'c';
		if (sz != s.capacity())
		{
			sz = s.capacity();
			cout << "capacity changed: " << sz << '\n';
		}
	}
}

运行结果:
在这里插入图片描述

四、clear/empty

clear: 清空整个字符串
empty: 判断该字符串是否为空

void test_string5()
{
	//clear:清空整个字符串
	s1.clear();
	s1.push_back('d'); //清空之后重新插入数据
	s1.push_back('d');
	s1.push_back('d');
	s1.push_back('d');
	s1.push_back('d');
	for (auto e : s1)//打印
	{
		cout << e << " ";
	}
	cout << endl;

	//empty
	s1.clear();
	if (s1.empty())
	{
		s1.push_back('a'); 
		s1.push_back('b');
	    s1.push_back('c'); 
	}
	for (auto e : s1)//打印
	{
		cout << e << " ";
	}
	cout << endl;
}

五、reserve和resize

reserve: 扩容
resize: 分三种情况

  1. 当传的值小于size小于capacity,直接缩小size到传递的值
  2. 当传的值大于size小于capacity,后面多出来size部分如果没有传值的话就初始化为0,如果传字符的话就初始化为传的字符,size变为传过来的大小,capacity暂时不变(因为不超过容量)
  3. 当传的值大于size大于capacity,后面多出来的部分如果没有传值的话就初始化为0,如果传字符的话就初始化为传的字符,size变为传递过来的值,capacity会增容(增容原理就是第一次二倍,以后基本是1.5倍)
void test_string6()
{
	//reserve和resize
	string s1("hello world");
	s1.reserve(100);
	cout << s1.size() << endl;//11
	cout << s1.capacity() << endl;//111

	string s2("hello world");
	s2.resize(5);//小于size小于capacity,直接缩小size
	cout << s2.size() << endl;//5
	cout << s2.capacity() << endl;//15(容量最开始就是15)
	cout << s2 << endl;

	string s3("hello world");
	s3.resize(14, 'a');//大于size小于capacity,后面的初始化为a,size变为14,capacity是15不变
	cout << s3.size() << endl;//14
	cout << s3.capacity() << endl;//15
	cout << s3 << endl;

	string s4("hello world");
	s4.resize(20, 'b');//大于size大于capacity,后面的初始化为x,size变为20,capacity会增容
	cout << s4.size() << endl;//20
	cout << s4.capacity() << endl;//31
	cout << s4 << endl;
}

运行结果:
在这里插入图片描述

六、查找某个字符对它进行更改

使用string的三种遍历方式都可以对某个字符进行更改,具体代码如下。

可以戳博主这篇文章:
C++:string的三种遍历方式(operator[ ],迭代器,新式for循环)

void test_string7()
{
	string s("hello,world");
	for (size_t i = 0; i < s.size();  i++)
	{
		if (s[i] == ',')
		{
			s[i] = '%';
		}
	}
	cout << s << endl;
	
	for (auto& e : s)
	{
		if (e == '%')
		{
			e = ',';
		}
	}
	cout << s << endl;

	string::iterator sit = s.begin();
	while (sit != s.end())
	{
		if (*sit == ',')
		{
			*sit = '%';
		}
		sit++;
	}
	cout << s << endl;

	size_t pos = s.find('%');
	s[pos] = ',';
	cout << s << endl;
}

运行结果:
在这里插入图片描述

七、关于字符串的追加

append: 这是一个函数。给某个对象追加某个对象,完成两个字符串的拼接
+=: 这是一个运算符的重载。同样可以实现一个字符串与一个字符串的拼接,这样的写法更加直观一些。
+: 这是一个运算符的重载。也可以实现一个字符串加一个字符串,但是这个运算符效率太低,不建议使用。

void test_string8()
{
	string s1("hello ");
	string s2("world");
	s1.append(s2);
	cout << s1 << endl;

	string s3("hello ");
	string s4("world");
	s3 += s4;
	s3 += "!!!";
	cout << s3 << endl;

	string s5("hello ");
	string s6("world");
	string s7 = s5 + s6;//不建议用+
	cout << s7 << endl;
}

运行结果:
在这里插入图片描述

八、insert/erase

insert: 在某个位置插入一个字符、一个字符串或一个对象
erase: 删除某位置的字符

void test_string9()
{
	string s1("ello");
	string s2(" world");
	s1.insert(0, 1, 'h');//在第0个位置的前面插入一个字符h
	cout << s1 << endl;

	s1.insert(s1.end(), 'w');//在end()位置,插入一个字符w
	cout << s1 << endl;

	s1.erase(5, 1);//从第五个位置开始删除,删除1个字符
	cout << s1 << endl;

	s1.insert(5, " world");//从第五个位置开始插入,插入一个字符串
	cout << s1 << endl;

	s1.insert(5, s2);//从第五个位置开始插入,插入一个对象s2
	cout << s1 << endl;
}

运行结果:
在这里插入图片描述

九、swap(两个字符串的交换)

string里实现了一个swap函数,这个swap函数是完成两个字符串的交换,底层实现的原理是交换指向的对象即可,消耗比较小,建议使用。

但是我们也知道C++库里也有一个swap函数,这个swap函数实现的原理是创建临时变量,不断交换赋值,这样对于string类就会消耗特别大,所以不建议使用C++库里的swap函数。

void test_string10()
{
	string s1("hello");
	string s2("world");
	s1.swap(s2);//string类里实现的swap,建议使用
	cout << s1 << "--" << s2 << endl;

	swap(s1, s2);//C++库里的swap,不建议使用,效率低下
	cout << s1 << "--" << s2 << endl;
}

运行结果:
在这里插入图片描述

十、replace和c_str

replace: 完成字符的替换
c_str: 以C语言的方式输出一个字符串(遇到‘\0’就会停止)

void test_string11()
{
	string s("http://www.cplusplus.com/");
	s.replace(0, 4, "https");//从第一位开始的四个字符替换为‘https’
	cout << s << endl;

	s[5] = '\0';
	cout << s << endl;//遇到\0不会结束,直到size才结束
	cout << s.c_str() << endl;//以C形式输出,遇到\0就会停止
}

运行结果:
在这里插入图片描述

十一、find和substr

find: 找某个字符的位置
substr: 获取子串

应用这两个接口实现取一个文件名的后置取一个网站的域名,代码如下:

string GetSuffix(const string& s)
{
	size_t pos = s.find('.');
	if (pos == string::npos)
	{
		return s;
	}
	else
	{
		//string suffix(s, pos, s.size() - pos);//构造
		string suffix = s.substr(pos);//获取子串:从pos取到最后
		return suffix;
	}
}
void test_string12()
{
	//取后缀
	string file("file.cpp");
	string suffix(file, 4, 4);
	cout << suffix << endl;

	size_t pos = file.find('.');//找到了返回第一次出现的位置,没找到返回npos(-1)
	if (pos != string::npos)//说明找到了
	{
		string suffix(file, pos, file.size()-pos);//构造函数:从file的pos(.)位置开始,取总长减pos个字符,拷贝构造给suffix
		cout << suffix << endl;
	}
	
	cout << GetSuffix("test.c.cpp") << endl;

	//取域名
	string url("http://www.cplusplus.com/reference/string/string/substr/");
	size_t start = url.find("://")+3;//找"://"字符串,然后+3记录最后一个/的位置
	size_t finish = url.find('/',start);//从刚刚记录的start位置开始找下一个'/'
	//start和finish之间的一段就是域名
	string domain=url.substr(start, finish-start);//从start开始输出,输出finish-start个字符(finish-start就是域名的字符个数)
	cout << domain << endl;
}

运行结果:
在这里插入图片描述

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值