目录简述
一、反转字符串
题目描述:
编写一个函数,其作用是将输入的字符串反转过来。输入字符串以字符数组 s
的形式给出。
不要给另外的数组分配额外的空间,你必须原地修改输入数组、使用 O(1) 的额外空间解决这一问题。
输入输出示例:
示例1:
输入:s = ["h","e","l","l","o"]
输出:["o","l","l","e","h"]
示例2:
输入:s = ["H","a","n","n","a","h"]
输出:["h","a","n","n","a","H"]
提示:
1 <= s.length <= 105
s[i]
都是 ASCII 码表中的可打印字符
思路和想法:
对同一个字符串里两个元素进行交换,中间只需一个字符变量来缓存即可。
class Solution {
public:
void reverseString(vector<char>& s) {
char tmp;
for(int i = 0, j = s.size() - 1; i < j; i++, j--){
tmp = s[i];
s[i] = s[j];
s[j] = tmp;
}
}
};
二、反转字符串2
题目描述:
给定一个字符串 s
和一个整数 k
,从字符串开头算起,每计数至 2k
个字符,就反转这 2k
字符中的前 k
个字符。
- 如果剩余字符少于
k
个,则将剩余字符全部反转。 - 如果剩余字符小于
2k
但大于或等于k
个,则反转前k
个字符,其余字符保持原样
输入输出示例:
示例1:
输入:s = "abcdefg", k = 2
输出:"bacdfeg"
示例2:
输入:s = "abcd", k = 2
输出:"bacd"
提示:
1 <= s.length <= 104
s
仅由小写英文组成1 <= k <= 104
思路和想法:
class Solution {
public:
string reverseStr(string s, int k) {
for (int i = 0; i < s.size(); i += (2 * k)) {
// 1. 每隔 2k 个字符的前 k 个字符进行反转
// 2. 剩余字符小于 2k 但大于或等于 k 个,则反转前 k 个字符
if (i + k <= s.size()) {
reverse(s.begin() + i, s.begin() + i + k );
} else {
// 3. 剩余字符少于 k 个,则将剩余字符全部反转。
reverse(s.begin() + i, s.end());
}
}
return s;
}
};
三、替换空格
题目描述:
请实现一个函数,把字符串 s
中的每个空格替换成"%20"。
输入输出示例:
示例1:
输入:s = "We are happy."
输出:"We%20are%20happy."
限制:
0 <= s 的长度 <= 10000
思路和想法:
步骤一:统计空格数量
步骤二:进行字符串的扩容
步骤三:进行字符串的替换
class Solution {
public:
string replaceSpace(string s) {
//步骤一,统计空格数量
int count = 0;
int size = s.size();
for(int i = 0; i < s.size(); i++){
if(s[i] == ' '){
count++;
}
}
//步骤二:进行扩容
s.resize(s.size() + count * 2);
int newSize = s.size();
//步骤三:进行字符串替换
for(int i = size - 1, j = newSize - 1; i < j; i--, j--){
if(s[i] != ' '){
s[j] = s[i];
}
else{
s[j] = '0';
s[j - 1] = '2';
s[j - 2] = '%';
j -= 2;
}
}
return s;
}
};
四、翻转字符串里的单词
题目描述:
给你一个字符串 s
,请你反转字符串中 单词 的顺序。
单词 是由非空格字符组成的字符串。s
中使用至少一个空格将字符串中的 单词 分隔开。
返回 单词 顺序颠倒且 单词 之间用单个空格连接的结果字符串。
注意:输入字符串 s
中可能会存在前导空格、尾随空格或者单词间的多个空格。返回的结果字符串中,单词间应当仅用单个空格分隔,且不包含任何额外的空格。
输入输出示例:
示例1:
输入:s = "the sky is blue"
输出:"blue is sky the"
示例2:
输入:s = " hello world "
输出:"world hello"
解释:反转后的字符串中不能存在前导空格和尾随空格。
示例3:
输入:s = "a good example"
输出:"example good a"
解释:如果两个单词间有多余的空格,反转后的字符串需要将单词间的空格减少到仅有一个。
提示:
1 <= s.length <= 104
s
包含英文大小写字母、数字和空格' '
s
中 至少存在一个 单词
思路和想法:
- 步骤一:去除空余空格
- 步骤二:将整个字符串翻转
- 步骤三:将每个单词反转
class Solution {
public:
void deleteSpace(string& s){
int slow = 0;
for(int fast = 0; fast < s.size();++fast){
if(s[fast] != ' '){
if(slow != 0){
s[slow++] = ' ';
}
while (fast < s.size() && s[fast] != ' ') {
s[slow++] = s[fast++];
}
}
}
s.resize(slow);
}
void reverse1(string& s, int start, int end){ //翻转,区间写法:左闭又闭 []
for (int i = start, j = end; i < j; i++, j--) {
swap(s[i], s[j]);
}
}
string reverseWords(string s) {
//步骤一,去除多余的空格
deleteSpace(s);
//步骤二,整个字符串进行翻转
reverse(s.begin(), s.end());
//步骤三,进行单词翻转
int start = 0;
for (int i = 0; i <= s.size(); ++i) {
if (i == s.size() || s[i] == ' ') { //到达空格或者串尾,说明一个单词结束。进行翻转。
reverse1(s, start, i - 1); //翻转,注意是左闭右闭 []的翻转。
start = i + 1; //更新下一个单词的开始下标start
}
}
return s;
}
};
五、左旋转字符串
题目描述:
字符串的左旋转操作是把字符串前面的若干个字符转移到字符串的尾部。请定义一个函数实现字符串左旋转操作的功能。比如,输入字符串"abcdefg"和数字2,该函数将返回左旋转两位得到的结果"cdefgab"。
输入输出示例:
示例1:
输入: s = "abcdefg", k = 2
输出: "cdefgab"
示例2:
输入: s = "lrloseumgh", k = 6
输出: "umghlrlose"
限制:
1 <= k < s.length <= 10000
思路和想法:
- 步骤一:反转区间前n的子串
- 步骤二:反转区间n到末尾的子串
- 步骤三:反转整个子串
class Solution {
public:
string reverseLeftWords(string s, int n) {
//步骤一:反转区间前n的子串
reverse(s.begin(), s.begin() + n);
//步骤二:反转区间n到末尾的子串
reverse(s.begin() + n, s.end());
//步骤三:反转整个字符串
reverse(s.begin(), s.end());
return s;
}
};