前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >STL介绍以及string类

STL介绍以及string类

作者头像
用户11039545
发布2024-08-20 09:49:54
1000
发布2024-08-20 09:49:54
举报
文章被收录于专栏:c语言

什么是STL

是C++标准库的重要组成部分,不仅是一个可复用的组件库,而且是一个包罗数据结构与算法的软件框架。

STL的六大组件

为什么要学习string类

C语言中的字符串

C语言中,字符串是以'\0'结尾的一些字符的集合,为了操作方便,C标准库中提供了一些str系列的库函数, 但是这些库函数与字符串是分离开的,不太符合OOP的思想,而且底层空间需要用户自己管理,稍不留神可能还会越界访问。

标准库中的string类

1.字符串是表示字符序列的类

2. 标准的字符串类提供了对此类对象的支持,其接口类似于标准字符容器的接口,但添加了专门用于操作单字节字符字符串的设计特性

3. string类是使用char

(即作为它的字符类型,使用它的默认char_traits和分配器类型(关于模板的更多信息,请参阅basic_string)

4. string类是basic_string模板类的一个实例,它使用char来实例化basic_string模板类,并用char_traits 和allocator作为basic_string的默认参数(根于更多的模板信息请参考basic_string)

5. 注意,这个类独立于所使用的编码来处理字节:如果用来处理多字节或变长字符(如UTF-8)的序列,这个类的所有成员(如长度或大小)以及它的迭代器,将仍然按照字节(而不是实际编码的字符)来操作

总结:

1. string是表示字符串的字符串类

2. 该类的接口与常规容器的接口基本相同,再添加了一些专门用来操作string的常规操作

3. string在底层实际是:basic_string模板类的别名,typedef basic_string string

4. 不能操作多字节或者变长字符的序列。 在使用string类时,必须包含#include头文件以及using namespace std。

string类的常用接口说明

string类对象的常见构造

string类对象的容量操作

1.size()与length()方法底层实现原理完全相同,引入size()的原因是为了与其他容器的接口保持一 致,一般情况下基本都是用size()。

2. clear()只是将string中有效字符清空,不改变底层空间大小。

3.resize(size_t n) 与 resize(size_t n, char c)都是将字符串中有效字符个数改变到n个,

不同的是当字符个数增多时:resize(n)用0来填充多出的元素空间,resize(size_t n, char c)用字符c来填充多出的元素空间。

注意:resize在改变元素个数时,如果是将元素个数增多,可能会改变底层容量的大小,如果是将元素个数减少,底string类对象的访问及遍历操作 层空间总大小不变。

4. reserve(size_t res_arg=0):为string预留空间,不改变有效元素个数,当reserve的参数小于 string的底层空间总大小时,reserver不会改变容量大小。

string类对象的访问及遍历操作

string类对象的修改操作

注意:

1. 在string尾部追加字符时,s.push_back(c) / s.append(1, c) / s += 'c'三种的实现方式差不多,一般情况下string类的+=操作用的比较多,+=操作不仅可以连接单个字符,还可以连接字符串

2. 对string操作时,如果能够大概预估到放多少字符,可以先通过reserve把空间预留好。

string类非成员函数

vs和g++下string结构的说明

vs下string的结构 string总共占28个字节,内部结构稍微复杂一点,先是有一个联合体,联合体用来定义string中字 符串的存储空间:

当字符串长度小于16时,使用内部固定的字符数组来存放

当字符串长度大于等于16时,从堆上开辟空间

这种设计也是有一定道理的,大多数情况下字符串的长度都小于16,那string对象创建好之后,内 部已经有了16个字符数组的固定空间,不需要通过堆创建,效率高。

其次:还有一个size_t字段保存字符串长度,一个size_t字段保存从堆上开辟空间总的容量

最后:还有一个指针做一些其他事情。 故总共占16+4+4+4=28个字节。

g++下string的结构

G++下,string是通过写时拷贝实现的,string对象总共占4个字节,内部只包含了一个指针,该指 针将来指向一块堆空间,内部包含了如下字段:

空间总大小

字符串有效长度

引用计数

指向堆空间的指针,用来存储字符串

string类的模拟实现

经典的string类问题

题目

LCR 192. 把字符串转换成整数 (atoi) - 力扣(LeetCode)

代码语言:javascript
复制
class Solution {
public:
    int myAtoi(string str) 
   {
        int res = 0, bindry = INT_MAX / 10;
        int i = 0, sign = 1, length = str.size();
        if(length == 0) return 0;
        while(str[i] == ' ')
            if(++i == length) return 0;
        if(str[i] == '-') sign = -1;
        if(str[i] == '-' || str[i] == '+') i++;
        for(int j = i; j < length; j++) {
            if(str[j] < '0' || str[j] > '9') break;
            if(res > bindry || res == bindry && str[j] > '7')
                return sign == 1 ? INT_MAX : INT_MIN;
            res = res * 10 + (str[j] - '0');
        }
        return sign * res;
    }
};

415. 字符串相加 - 力扣(LeetCode)

两个数字位数不同怎么处理,这里我们统一在指针当前下标处于负数的时候返回 0,等价于对位数较短的数字进行了补零操作。

代码语言:javascript
复制
class Solution {
public:
    string addStrings(string num1, string num2)
       {
        int i = num1.length() - 1, j = num2.length() - 1, add = 0;
        string ans = "";
        while (i >= 0 || j >= 0 || add != 0) {
            int x = i >= 0 ? num1[i] - '0' : 0;
            int y = j >= 0 ? num2[j] - '0' : 0;
            int result = x + y + add;
            ans.push_back('0' + result % 10);
            add = result / 10;
            i -= 1;
            j -= 1;
        }
        // 计算完以后的答案需要翻转过来
        reverse(ans.begin(), ans.end());
        return ans;
    }
};

. - 力扣(LeetCode)

方法一:

代码语言:javascript
复制
class Solution {  
public:  
    // 定义一个公开的成员函数isPalindrome,接受一个string类型的参数s,返回一个bool值  
    bool isPalindrome(string s) {  
        // 定义一个空字符串sgood,用于存放经过处理后的s的有效字符(即去除非字母数字字符并转换为小写)  
        string sgood;  
        // 遍历输入字符串s中的每个字符  
        for (char ch: s) {  
            // 如果当前字符是字母或数字(使用isalnum函数判断),则将其转换为小写(使用tolower函数)并添加到sgood中  
            if (isalnum(ch)) {  
                sgood += tolower(ch);  
            }  
        }  
        // 使用sgood的逆序迭代器(rbegin到rend)构造一个新的字符串sgood_rev,它包含了sgood的所有字符但顺序相反  
        string sgood_rev(sgood.rbegin(), sgood.rend());  
        // 返回sgood和sgood_rev是否相等,即原字符串s是否在经过处理后可以构成一个回文字符串  
        return sgood == sgood_rev;  
    }  
};
代码语言:javascript
复制
class Solution {
public:
    bool isPalindrome(string s) {
        int n = s.size();
        int left = 0, right = n - 1;
        while (left < right) {
            while (left < right && !isalnum(s[left])) {
                ++left;
            }
            while (left < right && !isalnum(s[right])) {
                --right;
            }
            if (left < right) {
                if (tolower(s[left]) != tolower(s[right])) {
                    return false;
                }
                ++left;
                --right;
            }
        }
        return true;
    }
};

字符串最后一个单词的长度_牛客题霸_牛客网 (nowcoder.com)

代码语言:javascript
复制
#include <iostream>
using namespace std;

int main() {
    string str;
    while (cin >> str) {
        if (cin.get() == '\n')
            cout << str.size();
    }
}

. - 力扣(LeetCode)

代码语言:javascript
复制
#include <iostream>
using namespace std;

int main() {
    string str;
    while (cin >> str) {
        if (cin.get() == '\n')
            cout << str.size();
    }
}

541. 反转字符串 II - 力扣(LeetCode)

思路:双指针

s[i] 的字符与 s[N - 1 - i] 的字符发生了交换的规律,因此我们可以得出如下双指针的解法:

代码语言:javascript
复制
class Solution 
{
public:
    void reverseString(vector<char>& s) 
    {
        int n = s.size();
        for (int left = 0, right = n - 1; left < right; ++left, --right) {
            swap(s[left], s[right]);
        }
    }
};

387. 字符串中的第一个唯一字符 - 力扣(LeetCode)

代码语言:javascript
复制
class Solution {
public:
    string reverseStr(string s, int k) {
        int n = s.length();
        for (int i = 0; i < n; i += 2 * k) {
            reverse(s.begin() + i, s.begin() + min(i + k, n));
        }
        return s;
    }
};
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2024-08-19,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 什么是STL
  • STL的六大组件
  • 为什么要学习string类
    • C语言中的字符串
    • 标准库中的string类
    • string类的常用接口说明
      • string类对象的常见构造
        • string类对象的容量操作
          • string类对象的访问及遍历操作
            • string类对象的修改操作
              • string类非成员函数
                • vs和g++下string结构的说明
                  • g++下string的结构
                  • string类的模拟实现
                    • 经典的string类问题
                    • 题目
                    相关产品与服务
                    容器服务
                    腾讯云容器服务(Tencent Kubernetes Engine, TKE)基于原生 kubernetes 提供以容器为核心的、高度可扩展的高性能容器管理服务,覆盖 Serverless、边缘计算、分布式云等多种业务部署场景,业内首创单个集群兼容多种计算节点的容器资源管理模式。同时产品作为云原生 Finops 领先布道者,主导开源项目Crane,全面助力客户实现资源优化、成本控制。
                    领券
                    问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档