【C/C++刷题集】string类(一)

🫧个人主页:小年糕是糕手

💫个人专栏:《C++》《Linux》《数据结构》《C语言》

🎨你不能左右天气,但你可以改变心情;你不能改变过去,但你可以决定未来!



目录

一、字符串最后一个单词的长度

二、验证回文串

三、字符串中的第一个唯一字符

四、反转字符串


一、字符串最后一个单词的长度

字符串最后一个单词的长度

这里我们看题目有一个注意点就是我们平常使用cin输入时遇到空格会停下来,在例子中我们可以看到他有A B C D,如果我们使用cin在遇到第一个A之后就会报错,所以这里我们要用到另一种输入方式:getline

他并不是一个成员函数,而是输入流的全局函数 getline(istream&, string&) (定义在 <string> 头文件中),作用是从输入流中读取一整行内容,存入 string 对象

cpp 复制代码
// 基础用法(读整行)
getline(输入流对象, string对象);
// 扩展用法(读至指定终止符)
getline(输入流对象, string对象, 终止字符);

思路:我们要读取最后一个单词的长度,大家肯定会想到我们从第一个字母开始遍历,遇到空格就跳过并且记录一下,直到遍历完整个字符串,然后我们就可以知道了有几个空格,找到最后一个空格所处的位置,然后记录下最后一个单词的长度即可,这确实是个可行的方法,但是过程过于冗余了,我们可以利用string类中重载的一个成员函数rfind:

  1. rfind(' ')从字符串末尾往前找第一个空格的位置
  2. 如果找到空格:最后一个单词的长度 = 字符串总长度 - (空格位置 + 1)(因为空格的下一个位置是最后一个单词的开头);
  3. 如果没找到空格(整个字符串是一个单词):最后一个单词的长度 = 字符串总长度

下面我们写代码前再去简单了解一下rfind成员函数:

string类的rfind从字符串末尾向前查找指定内容 的成员函数,返回匹配内容的起始下标(若未找到则返回string::npos),常用于定位最后一次出现的字符 / 子串。

  • 参数 1 :要查找的子串 / 字符(支持stringchar*char);
  • 参数 2 :查找的结束位置 (默认是string::npos,即从字符串末尾开始找);
  • 返回值 :匹配内容的起始下标;未找到则返回string::npos(一个代表 "无位置" 的常量)
cpp 复制代码
#include<iostream>
#include<string>
using namespace std;

int main()
{
	string str;
	//cin >> str;
	//cin检测到空格或换行就会结束,我们这里要使用getline成员函数
	getline(cin, str);

	size_t pos = str.rfind(' ');
	//找到最后一个空格所处位置
	//这里if里面的条件表示没有没找到 -- 找到了
	if (pos != string::npos)
	{
		cout << str.size() - (pos + 1) << endl;
	}
	else
	{
		cout << str.size() << endl;
	}
	return 0;
} 

string::npos 是 C++ std::string 类里的一个静态常量 ,核心含义是「无效的位置 / 未找到匹配内容 」------ 专门用来标记 find/rfind 等查找函数 "没找到目标" 的返回值。

❌ 错误用法:用 pos == -1 判断(因为 size_t 是无符号类型,-1 会被转换成 npos 的值,但写法不规范,且容易出错);

✅ 正确用法:必须用 pos != string::npos 判断 "是否找到",pos == string::npos 判断 "没找到"。

二、验证回文串

验证回文串

思路:我们主要就是去处理将大写字母转换成小写字母并且将非字母数字的字符全部过滤掉,然后得到一个串,我们知道string定义的一个串是有下标的,这时候我们就可以利用双指针法去遍历这个串判断是否回文

这其实我们可以使用一些函数来帮助我们实现,但是目前阶段我们还是主要看逻辑所以不用这些函数:

cpp 复制代码
class Solution {
public:
    bool isPalindrome(string s) {
        // 步骤1:过滤+转换(纯ASCII判断,无库函数)
        string blank_string;//定义了一个空串
        for (auto ch : s)
        {
            // 判断是否是大写字母
            if (ch >= 'A' && ch <= 'Z') 
            {
                // 大写转小写(ASCII+32)
                blank_string += ch + 32;
            }
            // 判断是否是小写字母
            else if (ch >= 'a' && ch <= 'z') 
            {
                blank_string += ch;
            }
            // 判断是否是数字字符
            else if (ch >= '0' && ch <= '9')
            {
                blank_string += ch;
            }
            // 非字母/数字:自动跳过(不加入blank_string)
        }

        // 步骤2:双指针验证回文(无库函数依赖)
        int left = 0;
        int right = blank_string.size() - 1;
        while (left < right)
        {
            if (blank_string[left] != blank_string[right]) 
            {
                return false;
            }
            left++;
            right--;
        }
        return true;
    }
};

三、字符串中的第一个唯一字符

字符串中的第一个唯一字符

思路:我们要找的是一个字符串,且他告诉我们了这个串只有小写字母,那我们不妨定义一个数组,首先全部初始化为0,然后使用范围for遍历字符串,将每个字母对应存在数组中,统计次数,然后我们就可以通过遍历数组找到数组中第一个出现次数为1的字符并且返回且索引,没有就返回-1

cpp 复制代码
class Solution {
public:
    int firstUniqChar(string s) 
    {
        //步骤1:统计每个小写字母的出现次数(数组索引对应字符,值对应次数)
        int count[26] = {0}; // 初始化为0(26个字母)
        for (char ch : s) 
        {
            count[ch - 'a']++; // 'a'对应索引0,'b'对应1,以此类推
        }

        // 步骤2:遍历原字符串,找第一个出现次数为1的字符
        for (int i = 0; i < s.size(); i++)
        {
            if (count[s[i] - 'a'] == 1) 
            {
                return i; // 返回索引
            }
        }

        // 步骤3:无唯一字符,返回-1
        return -1;
    }
};

四、反转字符串

反转字符串

思路:这其实是这几个题目中最简单的一个,但是题中出现了vector我怕大家不认识就放到了最后,大家先不关注,就当他也是string使用就好了,后续的博客会为大家细致讲解,这题其实不看这个很简单,我们只需要找到最后一个字符位置,和头字符位置互换即可,然后一个++,一个--即可解决问题,这里我们唯一需要注意的就是我们交换的时候可以使用string类中我们说过的swap成员函数:

cpp 复制代码
class Solution {
public:
    void reverseString(vector<char>& s) {
        if (s.empty())
            return;
        int start = 0;
        int end = s.size() - 1;
        while (start < end) {
            swap(s[start], s[end]);
            start++;
            end--;
        }
    }
};

相关推荐
m0_736919105 分钟前
模板元编程性能分析
开发语言·c++·算法
Terio_my7 分钟前
简要 Java 面试题学习
java·开发语言·学习
pen-ai12 分钟前
【YOLO系列】 YOLOv1 目标检测算法原理详解
算法·yolo·目标检测
wbs_scy18 分钟前
C++11:类新功能、lambda与包装器实战
开发语言·c++
永远睡不够的入22 分钟前
类和对象(中)
c++
飞鹰5131 分钟前
深度学习算子CUDA优化实战:从GEMM到Transformer—Week4学习总结
c++·人工智能·深度学习·学习·transformer
2301_7657031433 分钟前
C++中的职责链模式实战
开发语言·c++·算法
StandbyTime41 分钟前
《算法笔记》学习记录-第一章
c++·算法·算法笔记
近津薪荼1 小时前
优选算法——双指针8(单调性)
数据结构·c++·学习·算法
f狐0狸x1 小时前
【C++修炼之路】C++ list容器基本用法详解
开发语言·c++·list