1. 复原 IP 地址
转换为StringBuilder方便插入点
注意
插入三个点后还要判断最后一段是否合法
判断的条件
class Solution {
List<String> res = new ArrayList<>();
public List<String> restoreIpAddresses(String s) {
StringBuilder sb = new StringBuilder(s);
backTracking(sb, 0, 0);
return res;
}
public void backTracking(StringBuilder sb, int start, int count){
if(count == 3){
String temp = sb.substring(start, sb.length());
//判断最后一段
if(isValid(temp))
res.add(sb.toString());
return;
}
for(int i = start; i < sb.length(); i++){
//sunstring()截取 [)
String temp = sb.substring(start, i+1);
if(isValid(temp)){
sb.insert(i+1, '.'); //下一位插入点
backTracking(sb, i+2, ++count);// i+1+1 多了一个点
sb.deleteCharAt(i+1);
count--;
}else{
return;
}
}
}
public boolean isValid(String s){
// s不能以0开头,但是可以单独一个0
if(s.length() == 0 || s.length() > 3 || (s.charAt(0) == '0' && s.length() != 1))
return false;
int num = Integer.valueOf(s);
if(num > 255)
return false;
return true;
}
}
2. 子集
将每一个path都保存下来,即树的所有节点
class Solution {
List<List<Integer>> res = new ArrayList<>();
List<Integer> path = new ArrayList<>();
public List<List<Integer>> subsets(int[] nums) {
backTracking(nums, 0);
return res;
}
public void backTracking(int[] nums, int start){
res.add(new ArrayList<>(path));
if(path.size() == nums.length)
return;
for(int i = start; i < nums.length; i++){
path.add(nums[i]);
backTracking(nums, i+1);
path.remove(path.size() - 1);
}
}
}
3. 子集II
加入path前判断是否和同层的前一个元素相同
class Solution {
List<List<Integer>> res = new ArrayList<>();
List<Integer> path = new ArrayList<>();
public List<List<Integer>> subsetsWithDup(int[] nums) {
Arrays.sort(nums);
backTracking(nums, 0);
return res;
}
public void backTracking(int[] nums, int start){
res.add(new ArrayList<>(path));
if(start == nums.length){
return;
}
for(int i = start; i < nums.length; i++){
if(i > start && nums[i] == nums[i-1])
continue;
path.add(nums[i]);
backTracking(nums, i + 1);
path.remove(path.size() - 1);
}
}
}