STL |
您所在的位置:网站首页 › 鼠标滚轮结构拆解图片大全集 › STL |
STL—容器—string类
其实string类准确来说并不是容器,因为他出现的时间比STL要早,但是也可以说是容器吧。 1.为什么要学习string类? 1.1C语言当中的字符串C语言中,字符串是以’\0’结尾的一些字符的集合,为了操作方便,C标准库中提供了一些str系列的库函数,但是这些库函数与字符串是分离开的,不太符合OOP的思想,而且底层空间需要用户自己管理,稍不留神可能还会越界访问。 1.2面试题415. 字符串相加 - 力扣(LeetCode) 在OJ中,有关字符串的题目基本以string类的形式出现,而且在常规工作中,为了简单、方便、快捷,基本 都使用string类,很少有人去使用C库中的字符串操作函数。 2.标准库中的string类 2.1string类的了解string类的文档介绍 字符串是表示字符序列的类 标准的字符串类提供了对此类对象的支持,其接口类似于标准字符容器的接口,但添加了专门用于操作单字节字符字符串的设计特性。 string类是使用char(即作为它的字符类型,使用它的默认char_traits和分配器类型(关于模板的更多信息,请参阅basic_string)。 string类是basic_string模板类的一个实例,它使用char来实例化basic_string模板类,并用char_traits和allocator作为basic_string的默认参数(根于更多的模板信息请参考basic_string)。 注意,这个类独立于所使用的编码来处理字节:如果用来处理多字节或变长字符(如UTF-8)的序列,这个类的所有成员(如长度或大小)以及它的迭代器,将仍然按照字节(而不是实际编码的字符)来操作。 总结: string是表示字符串的字符串类 该类的接口与常规容器的接口基本相同,再添加了一些专门用来操作string的常规操作。 string在底层实际是:basic_string模板类的别名,typedef basic_string string; 不能操作多字节或者变长字符的序列。 在使用string类时,必须包含#include头文件以及using namespace std; 我们在包含头文件的时候经常会遇到两个比较容易混淆的头文件引用#include 和 #include ,两者的主要区别如下: #include是C语言的标准库,主要是对字符串进行操作的库函数,是基于char*进行操作的,例如常见的字符串操作函数stpcpy、strcat都是在该头文件里面声明的。 #include是C++语言的标准库,该库里面定义了string类,你可以包含这个头文件,然后定义一个字符串对象,对于字符串的操作就基于该对象进行,例如:string str; 一般来说,c++的头文件不会有.h的出现,比如 ———————————————— 文档方面,个人觉得这个比较好用 - C++ Reference 作为一个程序员,查文档是一个必须具备的基本素质,当遇到一个不熟悉的接口需要使用的时候,查文档就是最好的解决方法,因此我们需要学会怎么查文档。 2.2string类的常用接口说明 2.2.1.string类的常见构造c++98版本中全部的构造 实例: // 初识string类 // string类 有很多的接口和成员函数,我们主要得熟悉的使用其中的2成,剩下的8成需要我们去通过网络查询来解决 # include # includeusing namespace std; int main() {// 关于string类的构造string s1; // 构造string s2("string"); // 直接构造string s3(s2); // 拷贝构造// 上面这三个最常用string s4(10, 's'); // string类中的的不常用的特殊构造string s5("hello", 1, 3); // string类中的不常用的特殊构造 [这里如果给的不是3 是过大的值,那么就是npos,意思就是将字符串后面有多少给多少] 这些知识都可以查文档查到// 能使用 s[i] += 1; // 写 [这个相当于对取出来的字符+1,就相当于给其ASCII码值+1]}for (size_t i = 0; i string s1("hello, world");cout string s("hello, world");cout string s("hello, world");if (s.empty())cout s.push_back('c'); // 也可以s += 'c'if (sz != s.capacity()) // != 的时候就说明s进行了增容{sz = s.capacity(); // 将新容量给到szcout s.push_back('c'); // 也可以s += 'c'if (sz != s.capacity()) // != 的时候就说明s进行了增容{sz = s.capacity(); // 将新容量给到szcout s.push_back('c'); // 也可以s += 'c'if (sz != s.capacity()) // != 的时候就说明s进行了增容{sz = s.capacity(); // 将新容量给到szcout s.push_back('c'); // 也可以s += 'c'if (sz != s.capacity()) // != 的时候就说明s进行了增容{sz = s.capacity(); // 将新容量给到szcout cout s[i] += 1; // 写 [这个相当于对取出来的字符+1,就相当于给其ASCII码值+1]}for (size_t i = 0; i *it -= 1; // 写++it; // 迭代}it = s.begin(); // 重置while (it != s.end()){cout int val = 0;string::const_iterator cit = str.begin(); // 此时的str是const对象,返回的是const类型的迭代器类型while (cit != str.end()){val *= 10;val += (*cit - '0');}cout // 让val + 上取出来的数字,然后再*10, 循环,直至全部取出、val *= 10; val += (s[i] - '0'); // -'0'是因为 取出来的是字符 而不是整形, - 去'0'的ASCII值才是对应整形}cout string s("hello");const char* str = s.c_str();// str拿到的是const char* 类型。// 获取字符数组的首地址,用c语言中的字符串形式去遍历while (*str) // 只要*str不是\0就继续{cout string s("text.cpp"); // 如果我们想查询这个后缀.cpp// 我们就可以用find去查询. 再将其后边的打印出来size_t pos = s.find('.'); // pos = 4if (pos != string::npos) // npos是-1 size_t的-1相当于int类型的最大值,42亿多{// 用substr接口实现.后的打印cout // 用substr接口实现.后的打印cout string url("https://gitee.com/wzf-sang");//https是协议 http和https的差别就是https是加密的///gitee.com其实是个ip但是绑定了域名。如果不绑定域名这里是个ip【域名更好记住】//wzf-sang就是资源名称。//【在我们输入网址敲回车之后,服务器做的第一件事就是将你输入的网址拆成协议、域名、资源名称】//【因此才能在对应协议下申请访问对应的域名并根据资源名称返回资源】// 现在有个要求:分离出url。size_t i1 = url.find(':'); // i1 = 5if (i1 != string::npos){cout //【在我们输入网址敲回车之后,服务器做的第一件事就是将你输入的网址拆成协议、域名、资源名称】//【因此才能在对应协议下申请访问对应的域名并根据资源名称返回资源】// 现在有个要求:分离出url。size_t i1 = url.find(':'); // i1 = 5if (i1 != string::npos){cout string url("https://gitee.com/wzf-sang");string url2("https://leetcode.cn/problems/majority-element/description/?envType=study-plan-v2&envId=top-interview-150");//https是协议 http和https的差别就是https是加密的///gitee.com其实是个ip但是绑定了域名。如果不绑定域名这里是个ip【域名更好记住】//wzf-sang就是资源名称。spilt_url(url);// https// gitee.com// wzf - sangspilt_url(url2);//https//leetcode.cn//problems/majority-element/description/?envType=study-plan-v2&envId=top-interview-150return 0; } 2.2.5string类非成员函数上面的几个接口了解一下,下面的OJ题目中会有一些体现他们的使用。string类中还有一些其他的操作,这里不一一列举,在需要用到时不明白了查文档即可。 2.2.6.vs和g++下string结构的说明注意:下述结构是在32位平台下进行验证,32位平台下指针占4个字节。 vs下string的结构string总共占28个字节,内部结构稍微复杂一点,先是有一个联合体,联合体用来定义string中字 符串的存储空间: 当字符串长度小于16时,使用内部固定的字符数组来存放 当字符串长度大于等于16时,从堆上开辟空间 这种设计是合理的,大多数情况下字符串的长度都小于16,那string对象创建好之后,内 部已经有了16个字符数组的固定空间,不需要通过堆创建,效率高。 其次:还有一个size_t字段保存字符串长度,一个size_t字段保存从堆上开辟空间总的容量 最后:还有一个指针做一些其他事情。 故总共占16+4+4+4=28个字节 G++下,string是通过写时拷贝实现的,string对象总共占4个字节,内部只包含了一个指针,该指 针将来指向一块堆空间,内部包含了如下字段: 空间总大小 字符串有效长度 引用计数 struct _Rep_base {size_type _M_length;size_type _M_capacity;_Atomic_word _M_refcount; }; 指向堆空间的指针,用来存储字符串。 2.2.7与string相关的oj题目917. 仅仅反转字母 - 力扣(LeetCode) 387. 字符串中的第一个唯一字符 - 力扣(LeetCode) 字符串最后一个单词的长度 125. 验证回文串 - 力扣(LeetCode) 415. 字符串相加 - 力扣(LeetCode) 541. 反转字符串 II - 力扣(LeetCode) 557. 反转字符串中的单词 III - 力扣(LeetCode) 43. 字符串相乘 - 力扣(LeetCode)较难 找出字符串中第一个只出现一次的字符较难 |
今日新闻 |
点击排行 |
|
推荐新闻 |
图片新闻 |
|
专题文章 |
CopyRight 2018-2019 实验室设备网 版权所有 win10的实时保护怎么永久关闭 |