[LeetCode] 1370. Increasing Decreasing String 上升下降字符串
You are given a string s. Reorder the string using the following algorithm:
- Remove the smallest character from
sand append it to the result. - Remove the smallest character from
sthat is greater than the last appended character, and append it to the result. - Repeat step 2 until no more characters can be removed.
- Remove the largest character from
sand append it to the result. - Remove the largest character from
sthat is smaller than the last appended character, and append it to the result. - Repeat step 5 until no more characters can be removed.
- Repeat steps 1 through 6 until all characters from
shave been removed.
If the smallest or largest character appears more than once, you may choose any occurrence to append to the result.
Return the resulting string after reordering s using this algorithm.
Example 1:
Input: s = "aaaabbbbcccc"
Output: "abccbaabccba"
Explanation: After steps 1, 2 and 3 of the first iteration, result = "abc"
After steps 4, 5 and 6 of the first iteration, result = "abccba"
First iteration is done. Now s = "aabbcc" and we go back to step 1
After steps 1, 2 and 3 of the second iteration, result = "abccbaabc"
After steps 4, 5 and 6 of the second iteration, result = "abccbaabccba"
Example 2:
Input: s = "rat"
Output: "art"
Explanation: The word "rat" becomes "art" after re-ordering it with the mentioned algorithm.
Constraints:
1 <= s.length <= 500sconsists of only lowercase English letters.
这道题说是给了一个字符串s,让采取下面一系列的措施:
- 删除s中最小的字符并将其附加到结果中。
- 删除比上次附加的字符大的s中最小的字符,并将其附加到结果中。
- 重复步骤2,直到不能再删除任何字符。
- 删除s中最大的字符并将其附加到结果中。
- 删除比上次附加的字符小的s中最大的字符,并将其附加到结果中。
- 重复步骤5,直到不能再删除任何字符。
- 重复步骤1到6,直到所有字符从s中被删除。
那么实际上就是找每个状态下s中的最大或最小的字符以及其个数,所以就需要统计每个字符出现的次数,而且最好还要能很方便的知道最大最小的字符是什么。一般来说,如果只想统计每个字符出现的个数,会用 HashMap 来做,但是这道题明确说了需要知道最大和最小的字符,则就应该用 TreeMap 或者数组来做。这里用数组来做更方便一点,因为题目中限定了字符串s中只有 26 个小写字母,则用一个大小为 26 的数组来统计每个字母的出现次数即可,而遍历的方向就可以决定取最大或最小的字符。由于总体步骤是要循环执行的,所以最外层要套一个 while 循环,判定条件就是结果 res 的长度不等于原字符串s。
然后从头开始遍历统计字符个数的数组 charCnt,若某个字符个数自减1之后仍大于等于0,则说明该字符存在,并且是当前最大的字符,则将其加入结果 res 中,这样保证了每种字符只会取一个,这样一圈遍历下来步骤1至3就完成了。同理,从末尾往前遍历,若某个字符个数自减1之后仍大于等于0,则说明该字符存在,并且是当前最小的字符,则将其加入结果 res 中,这样保证了每种字符只会取一个,这样一圈遍历下来步骤4至6就完成了。同时最外层的循环保证了步骤1至6可以重复执行,最终循环退出后就得到符合要求的结果 res,参见代码如下:
class Solution {
public:
string sortString(string s) {
string res;
vector<int> charCnt(26);
for (char c : s) {
++charCnt[c - 'a'];
}
while (s.size() != res.size()) {
for (int i = 0; i < 26; ++i) {
if (--charCnt[i] >= 0) {
res += (i + 'a');
}
}
for (int i = 25; i >= 0; --i) {
if (--charCnt[i] >= 0) {
res += (i + 'a');
}
}
}
return res;
}
};
Github 同步地址:
https://github.com/grandyang/leetcode/issues/1370
参考资料:
https://leetcode.com/problems/increasing-decreasing-string
https://leetcode.com/problems/increasing-decreasing-string/solutions/533002/c-counts/


浙公网安备 33010602011771号