7.1组合问题
class Solution {
public:
vector<vector<int>> result;
vector<int> path;//每一次的路径
void getpath(int n,int k,int startindex){
if(path.size()==k){//如果单次路径长度等于k则结束
result.push_back(path);
return;
}
for(int i=startindex;i<=n;i++){//startindex相当于下一个兄弟结点的起始值不能重复。
path.push_back(i);
getpath(n,k,i+1);//[1,*]这里1全部遍历完,下一次寻找的应该是[2,*]
path.pop_back();
}
}
vector<vector<int>> combine(int n, int k) {
getpath(n,k,1);
return result;
}
};
7.2组合总和Ⅲ
class Solution {
public:
vector<vector<int>> result;
vector<int> path;
void getpath(int targetsum,int k,int sum,int startindex){
if(path.size()==k){
if(sum==targetsum){//需要加一个相等的判断
result.push_back(path);
return;
}
}
for(int i=startindex;i<=9;i++){
sum += i;
path.push_back(i);
getpath(targetsum,k,sum,i+1);
path.pop_back();
sum -= i;//回溯
}
}
vector<vector<int>> combinationSum3(int k, int n) {
getpath(n,k,0,1);
return result;
}
};
7.3电话号码的字母组合
class Solution {
private:
const string lettermap[10] = {//const代表常量
"",//0
"",//1
"abc",//2
"def",//3
"ghi",//4
"jkl",//5
"mno",//6
"pqrs",//7
"tuv",//8
"wxyz",//9
};
public:
vector<string> result;
string path;
void getpath(string& digits,int index){//index代表遍历第几个数字,代表树的高度
if(digits.size()==index){
result.push_back(path);
return;
}
int digit = digits[index]-'0';//获得输入的第一个数字,再根据数字一个个找出对应的字母集
string letter = lettermap[digit];//获取具体的字母信息
for(int i=0;i<letter.size();i++){
path.push_back(letter[i]);
getpath(digits,index+1);
path.pop_back();
}
return;
}
vector<string> letterCombinations(string digits) {
if(digits.size()==0)
return result;
getpath(digits,0);
return result;
}
};
7.4组合总和
class Solution {
public:
vector<vector<int>> result;
vector<int> path;
void getpath(vector<int>& candidates,int sum,int index,int target){
if(sum>target)
return;
if(sum == target){//sum等于或者大于目标值target才返回
result.push_back(path);
return;
}
for(int i=index;i<candidates.size();i++){
sum += candidates[i];
path.push_back(candidates[i]);
getpath(candidates,sum,i,target);//此时不是i+1,因为本身也可以重复
sum -= candidates[i];
path.pop_back();
}
return;
}
vector<vector<int>> combinationSum(vector<int>& candidates, int target) {
getpath(candidates,0,0,target);
return result;
}
};
7.5组合总和Ⅱ
class Solution {
public:
vector<vector<int>> result;
vector<int> path;
void getpath(vector<int>& candidates,int target,int sum,int startindex,vector<bool>& used){
if(sum>target)
return;
if(sum == target){
result.push_back(path);
return;
}
for(int i=startindex;i<candidates.size() ;i++){
if(i>0 && candidates[i]==candidates[i-1] && used[i-1]==false)//此时used用来判断同一层树是否重复读取
continue;
sum += candidates[i];
path.push_back(candidates[i]);
used[i] = true;
getpath(candidates,target,sum,i+1,used);
used[i] = false;
sum -= candidates[i];
path.pop_back();
}
return;
}
vector<vector<int>> combinationSum2(vector<int>& candidates, int target) {
vector<bool> used(candidates.size(),false);
sort(candidates.begin(),candidates.end());//将相同的数值放在相邻的位置,方便当前值与前一个值相互比较
getpath(candidates,target,0,0,used);
return result;
}
};
7.6分割回文串
class Solution {
public:
vector<vector<string>> result;
vector<string> path;
void getpath(string s,int startindex){
if(startindex >= s.size()){//此时起始点大于等于字符串s的长度就说明有新的组合
result.push_back(path);
return;
}
for(int i=startindex;i<s.size();i++){
if(ishuiwen(s,startindex,i)){//判断是否回文
string str = s.substr(startindex,i-startindex+1);
path.push_back(str);
}
else
continue;
getpath(s,i+1);
path.pop_back();
}
return;
}
bool ishuiwen(string s,int start,int end){
for(int i=0,j=end;i<j;i++,j--)
if(s[start]!=s[end])
return false;
return true;
}
vector<vector<string>> partition(string s) {
getpath(s,0);
return result;
}
};
7.7复原IP地址
class Solution {
public:
vector<string> result;
void getpath(string& s,int startindex,int pointnum){
if(pointnum==3){//出现3个点说明已经分割成4个部分
if(isvaild(s,startindex,s.size()-1))//[startindex,s.size()-1]
result.push_back(s);
return;
}
for(int i=startindex;i<s.size();i++){
if(isvaild(s,startindex,i)){
pointnum++;
s.insert(s.begin()+i+1,'.');
getpath(s,i+2,pointnum);
pointnum--;
s.erase(s.begin()+i+1);
}
else
break;
}
}
bool isvaild(string s,int start,int end){
if(start>end)
return false;
if(s[start]=='0' && start != end)//0不可出现在开头,除非本身就没有数字只是0
return false;
int num = 0;
for(int i=start;i<=end;i++){
if(s[i]>'9'|| s[i]<'0')//只会出现0-9的数字
return false;
num = num*10+(s[i]-'0');
if(num>255)
return false;
}
return true;
}
vector<string> restoreIpAddresses(string s) {
if(s.size()<4||s.size()>12)
return result;
getpath(s,0,0);
return result;
}
};