题目:1190. 反转每对括号间的子串
难度: 中等
题目:
给出一个字符串 s(仅含有小写英文字母和括号)。
请你按照从括号内到外的顺序,逐层反转每对匹配括号中的字符串,并返回最终的结果。
注意,您的结果中 不应 包含任何括号。
示例1
输入:s = “(abcd)”
输出:“dcba”
示例2
输入:s = “(u(love)i)”
输出:“iloveu”
示例3
输入:s = “(ed(et(oc))el)”
输出:“leetcode”
示例4
输入:s = “a(bcdefghijkl(mno)p)q”
输出:“apmnolkjihgfedcbq”
提示:
0 <= s.length <= 2000
s 中只有小写英文字母和括号
- 我们确保所有括号都是成对出现的
`
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/reverse-substrings-between-each-pair-of-parentheses/
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
解题思路
作为括号匹配的问题,使用栈进行求解。本题要求我们将括号间的字符串翻转,那么可以再遇到括号时入栈,遇到反括号出栈并翻转求解。
解题代码
(1)栈
定义一个栈,遇到括号时将字符串压入栈中,然后每次对栈顶元素操作,遇到反括号时元素出栈并反转。
class Solution {
public:
string reverseParentheses(string s) {
int n = s.size();
int i = 0;
stack<string> stk;
string str;
string ans;
while (i < n)
{
if (s[i] == '(')
{
stk.push(str);
str = "";
}
else if (s[i] == ')')
{
string tmp = stk.top();
stk.pop();
string val(tmp.rbegin(), tmp.rend());//翻转
if (stk.empty())
{
ans += val;
}
else
{
stk.top() += val;
}
}
else
{
if (stk.empty())//栈为空
{
ans.push_back(s[i]);
}
else
{
stk.top().push_back(s[i]);
}
}
i++;
}
//cout << str << endl;
return ans;
}
};
(2)栈——优化
上面解法1可以优化,因为我们每次遇到括号时,将原来的数据存储在栈中,那么接下来就对str进行操作即可;遇到反括号时,将str反转,将栈顶元素取出,新的str = 栈顶元素 + str。而之前的操作,是每次对栈顶元素操作,遇到括号时将栈顶元素反转。
class Solution {
public:
string reverseParentheses(string s) {
int n = s.size();
stack<string> stk;
string str;
for (auto& ch : s)
{
if (ch == '(')
{
stk.push(str);
str = "";
}
else if (ch == ')')
{
reverse(str.begin(), str.end());
str = stk.top() + str;
stk.pop
}
else
{
str.push_back(ch);
}
}
return str;
}
};