题目1:93. 复原 IP 地址 - 力扣(LeetCode)
这道题和分割回文串 比较相似,主要是终止条件,通过设置IP的点来进行判断,如果 pointnum == 3 说明已经分割出四个字符串了,就可以终止,前面三个 再for循环里判断了,但是最后一个需要再终止条件里进行判断,我选择用一个数组存储字符串最后再拼合,这个比较麻烦但是感觉相比再字符里直接加点清晰明了一些。不过要注意最后一个字符串加入path 也要进行pop回溯。之后判断是否合法,首先是 begin > end 不对, 头不能是0, 不能有数字以外的非法字符,字符数不能大于255。这里判断字符不能加完所有的再判断,否则会超过数据类型的上界,在for循环里进行判断,只要前几位有大于255一定大于就返回false就行。
class Solution {
public:
vector<string> path;
vector<string> reslut;
void backtracking(string s, int startindex, int pointnum) {
if(pointnum == 3) {
if(isvalid(s, startindex, s.size() - 1)) {
path.push_back(s.substr(startindex, s.size() - startindex));
string _tmp;
for(int i =0;i < path.size() - 1;i++) {
_tmp += path[i];
_tmp += ".";
}
_tmp += path[path.size() - 1];
path.pop_back();
reslut.push_back(_tmp);
return;
}
}
for(int i = startindex;i < s.size();i++) {
if(isvalid(s, startindex, i)) {
path.push_back(s.substr(startindex, i - startindex + 1));
pointnum++;
backtracking(s, i + 1, pointnum);
path.pop_back();
pointnum--;
}
}
}
bool isvalid(string s, int begin, int end) {
if(begin > end) return false;
string tmp = s.substr(begin, end - begin + 1);
if(tmp.size() > 1 && tmp[0] == '0') return false;
int tmpnum = 0;
for(int i = 0;i < tmp.size();i++) {
if(tmp[i] < '0' || tmp[i] > '9') return false;
tmpnum = tmpnum * 10 + tmp[i] - '0';
if(tmpnum > 255) return false;
}
return true;
}
vector<string> restoreIpAddresses(string s) {
backtracking(s, 0, 0);
return reslut;
}
};
这道题不是在满足条件之后再收集结果,是再每次for循环的时候,就将path放入到reslut,自己AC过了,代码:
class Solution {
public:
vector<int> path;
vector<vector<int>> reslut;
void backtracking(vector<int>& nums, int startindex) {
if(startindex == nums.size()) {
return;
}
for(int i = startindex;i < nums.size();i++) {
path.push_back(nums[i]);
reslut.push_back(path);
backtracking(nums, i + 1);
path.pop_back();
}
}
vector<vector<int>> subsets(vector<int>& nums) {
reslut.push_back({});
backtracking(nums, 0);
return reslut;
}
};
这道题确实和之前的组合II很像,首先要将数组排序,然后相同的元素只取第一个,这里可以通过设置一个bool 的数组 进行判断,还可以通过 if(i > startindex && nums[i] == nums[i - 1]) 这个其实就是当前元素是否和前面 的元素一样,代码如下:
class Solution {
public:
vector<int> path;
vector<vector<int>> reslut;
void backtracking(vector<int>& nums, int startindex) {
if(startindex == nums.size()) {
return;
}
for(int i = startindex;i < nums.size();i++) {
if(i > startindex && nums[i] == nums[i - 1]) continue;
else path.push_back(nums[i]);
reslut.push_back(path);
backtracking(nums, i + 1);
path.pop_back();
}
}
vector<vector<int>> subsetsWithDup(vector<int>& nums) {
reslut.push_back({});
sort(nums.begin(), nums.end());
backtracking(nums, 0);
return reslut;
}
};