我的解法(元素顺序和答案不对)
思路:
- 简单测试了一下之后,发现我只需要构造该vector<string>中元素即可。不需要我输出“[]”和“”。
- n=1时,item应该是“()”;
- n=2时,item有2个:“(())”和“()()”;
- n=3时,item有5个:"((()))"、"(()())"、"(())()"、"()(())"、"()()()"
- 我找到的规律是:(1)先给上一个结果中的每个元素加外括号"()" (2)给上一个结果的最后一个加一个小括号"()" (3)分别除最后一个元素外的其他元素,右侧和左侧分别加括号"()"、"()"
代码:
class Solution {
public:
vector<string> generateParenthesis(int n)
{
vector<string> ans;
if(n==1)
{
string item="()";
ans.push_back(item);
}
else
{
vector<string> last=generateParenthesis(n-1);//取得上次结果的所有元素
string item;
for(int j=0;j<last.size();j++)
{
item="("+last[j]+")";//给每一个元素的外面加一个括号
ans.push_back(item);
}
for(int j=0;j<last.size()-1;j++)
{
item=last[j]+"()"; //除了最后一个之外,在右边加括号
ans.push_back(item);
}
for(int j=0;j<last.size()-1;j++)
{
item="()"+last[j]; //除了最后一个之外,在左边加括号
ans.push_back(item);
}
item=last[last.size()-1]+"()";//最后一个在右边加括号
ans.push_back(item);
}
return ans;
}
};
评论:明明题目中说,得到所有结果即可呀!为什么还要对顺序作要求呢?看来是有固定解法。
正确解法:
看了solution,也看了几个博主的答案后,终于理解了这种思路。
思路:
- 溯源算法:可以理解为是一种试探性的全局搜索。穷举出每一种可能性,把所有成功的解都返回解空间的一种算法。
(对于这种列出所有结果的题首先还是考虑用递归Recursion来解。)
- 递归:在理解递归的时候不要进入函数的内部做嵌套,而应该把他理解成一个黑盒子。彻底把函数抽象出来,只考虑函数的输入输出,实现效果。
- 递归过程:
-
回归条件:逐步生成左右括号,当数量都达到最大值n时,那么把解返回解空间。
选择条件1:如果左括号还不够,那么就递归。
递归关系: 如果左括号还不够,那么就用掉一个左括号(字符串+“(”,函数中left-1)
选择条件2:如果右括号小于左括号数量,那么就递归。(如果在某次递归时,字符串中右括号的个数大于左括号的个数,即会出现')('这样的非法串,所以这种情况不处理。)
递归关系: 用掉一个右括号。
-
递归是怎么回退的?dfs。深度优先搜索。如下图所示(源自讨论区):n=2时的所有情况。只有满足leftNum<=2,和rightNum<=leftNum的才可以。

代码:
class Solution {
public:
void generate(vector<string>&ans,string curStr,int leftNum,int rightNum,int max){
if(leftNum==max&&rightNum==max){
ans.push_back(curStr);
return;
}
if(leftNum<max) {
generate(ans,curStr+"(",leftNum+1,rightNum,max);
}
if(rightNum<leftNum){
generate(ans,curStr+")",leftNum,rightNum+1,max);
}
}
vector<string> generateParenthesis(int n)
{
vector<string> ans;
generate(ans,"",0,0,n);
return ans;
}
};
828

被折叠的 条评论
为什么被折叠?



