You are given a string s
and two integers x
and y
. You can perform two types of operations any number of times.
- Remove substring
"ab"
and gainx
points.- For example, when removing
"ab"
from"cabxbae"
it becomes"cxbae"
.
- For example, when removing
- Remove substring
"ba"
and gainy
points.- For example, when removing
"ba"
from"cabxbae"
it becomes"cabxe"
.
- For example, when removing
Return the maximum points you can gain after applying the above operations on s
.
Example 1:
Input: s = "cdbcbbaaabab", x = 4, y = 5 Output: 19 Explanation: - Remove the "ba" underlined in "cdbcbbaaabab". Now, s = "cdbcbbaaab" and 5 points are added to the score. - Remove the "ab" underlined in "cdbcbbaaab". Now, s = "cdbcbbaa" and 4 points are added to the score. - Remove the "ba" underlined in "cdbcbbaa". Now, s = "cdbcba" and 5 points are added to the score. - Remove the "ba" underlined in "cdbcba". Now, s = "cdbc" and 5 points are added to the score. Total score = 5 + 4 + 5 + 5 = 19.
Example 2:
Input: s = "aabbaaxybbaabb", x = 5, y = 4 Output: 20
Constraints:
1 <= s.length <= 105
1 <= x, y <= 104
s
consists of lowercase English letters.
Solution: Greedy + Stack
Remove the pattern with the larger score first.
Using a stack to remove all occurrences of a pattern in place in O(n) Time.
Time complexity: O(n)
Space complexity: O(1)
C++
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
// Author: Huahua class Solution { public: int maximumGain(string s, int x, int y) { // Remove patttern p from s for t points each. // Returns the total score. auto remove = [&](const string& p, int t) { int total = 0; int i = 0; for (int j = 0; j < s.size(); ++j, ++i) { s[i] = s[j]; if (i && s[i - 1] == p[0] && s[i] == p[1]) { i -= 2; total += t; } } s.resize(i); return total; }; string px{"ab"}; string py{"ba"}; if (y > x) { swap(px, py); swap(x, y); } return remove(px, x) + remove(py, y); } }; |