17:电话号码的字母组合
class Solution {
public List<String> letterCombinations(String digits) {
if(digits == null || digits.isEmpty()){
return new ArrayList<>();
}
Map<Character, String> map = getMap();
List<String> res = new ArrayList<>();
StringBuilder sb = new StringBuilder();
dfs(map, digits.toCharArray(), 0, digits.length(), sb, res);
return res;
}
private void dfs(Map<Character, String> map, char[] chars, int index, int len, StringBuilder sb, List<String> res){
if(index == len){
res.add(sb.toString());
return;
}
String digitStr = map.get(chars[index]);
for(char c : digitStr.toCharArray()){
sb.append(c);
dfs(map, chars, index + 1, len, sb, res);
sb.setLength(sb.length() - 1);
}
}
private Map<Character, String> getMap(){
Map<Character, String> map = new HashMap<>();
map.put('2', "abc");
map.put('3', "def");
map.put('4', "ghi");
map.put('5', "jkl");
map.put('6', "mno");
map.put('7', "pqrs");
map.put('8', "tuv");
map.put('9', "wxyz");
return map;
}
}
22:括号生成
class Solution {
public List<String> generateParenthesis(int n) {
if(n < 1){
return Arrays.asList("");
}
if(n < 2){
return Arrays.asList("()");
}
List<String> res = new ArrayList<>();
StringBuilder sb = new StringBuilder();
dfs(n, 0, 0, res, sb);
return res;
}
private void dfs(int n, int leftCnt, int rightCnt, List<String> res, StringBuilder sb){
if(leftCnt == n && rightCnt == n){
res.add(sb.toString());
}
if(leftCnt < n){
sb.append("(");
dfs(n, leftCnt + 1, rightCnt, res, sb);
sb.setLength(sb.length() - 1);
}
if(rightCnt < leftCnt){
sb.append(")");
dfs(n, leftCnt, rightCnt + 1, res, sb);
sb.setLength(sb.length() - 1);
}
}
}
37:解数独
39:组合总和
class Solution {
public List<List<Integer>> combinationSum(int[] candidates, int target) {
List<List<Integer>> res = new ArrayList<>();
List<Integer> tempList = new ArrayList<>();
back(res, tempList, candidates, target, 0);
return res;
}
private void back(List<List<Integer>> res, List<Integer> tempList, int[] candidates, int target, int start){
if(target < 0){
return;
}
if(target == 0){
res.add(new ArrayList<>(tempList));
return;
}
for(int i = 0; i < candidates.length; i++){
int temp = candidates[i];
tempList.add(temp);
back(res, tempList, candidates, target - temp, i);
tempList.remove(tempList.size() - 1);
}
}
}
40:组合总和II
class Solution {
public List<List<Integer>> combinationSum2(int[] candidates, int target) {
List<List<Integer>> res = new ArrayList<>();
List<Integer> list = new ArrayList<>();
Arrays.sort(candidates);
huisu(res, list, candidates, target, 0);
return res;
}
private void huisu(List<List<Integer>> res, List<Integer> list, int[] candidates, int target, int start){
if(target == 0){
res.add(new ArrayList<>(list));
return;
}
for(int i = start; i < candidates.length; i++){
if(candidates[i] > target){
continue;
}
if(i > start && candidates[i] == candidates[i - 1]){
continue;
}
list.add(candidates[i]);
huisu(res, list, candidates, target - candidates[i], i + 1);
list.remove(list.size() - 1);
}
}
}
46:全排列
class Solution {
public List<List<Integer>> permute(int[] nums) {
List<List<Integer>> res = new ArrayList<>();
List<Integer> tempList = new ArrayList<>();
dfs(nums, res, tempList);
return res;
}
private void dfs(int[] nums, List<List<Integer>> res, List<Integer> tempList){
if(tempList.size() == nums.length){
res.add(new ArrayList<>(tempList));
return;
}
for(int i = 0; i < nums.length; i++){
if(tempList.contains(nums[i])){
continue;
}
tempList.add(nums[i]);
dfs(nums, res, tempList);
tempList.remove(tempList.size() - 1);
}
}
}
47:全排列II
class Solution {
public List<List<Integer>> permuteUnique(int[] nums) {
List<List<Integer>> res = new ArrayList<>();
if(nums == null || nums.length == 0){
return res;
}
int len = nums.length;
Arrays.sort(nums);
Deque<Integer> queue = new ArrayDeque<>(len);
boolean[] indexArr = new boolean[len];
dfs(nums, len, 0, queue, indexArr, res);
return res;
}
private void dfs(int[] nums, int len, int level, Deque<Integer> queue, boolean[] indexArr, List<List<Integer>> res){
if(level == len){
res.add(new ArrayList<>(queue));
return;
}
for(int i = 0; i < len; i++){
if(indexArr[i]){
continue;
}
if(i > 0 && nums[i] == nums[i-1] && indexArr[i-1]){
break;
}
indexArr[i] = true;
queue.offerLast(nums[i]);
dfs(nums, len, level + 1, queue, indexArr, res);
indexArr[i] = false;
queue.pollLast();
}
}
}
51:N皇后
class Solution {
public List<List<String>> solveNQueens(int n) {
char[][] chess = new char[n][n];
for(int i = 0; i < n; i++){
for(int j = 0; j < n; j++){
chess[i][j] = '.';
}
}
solve(chess, 0);
return chess;
}
private void solve(char[][] chess, int row){
for(int col = 0; col < chess.length; col++){
if(valid(chess, row, col)){
char[][] temp = copy(chess);
temp[row][col] = 'Q';
solve(chess, row + 1);
}
}
}
private char[][] copy(char[][] chess){
char[][] temp = new char[chess.length][chess[0].length];
for(int i = 0; i < chess.length; i++){
for(int j = 0; j < chess[0].length; j++){
temp[i][j] = chess[i][j];
}
}
return temp;
}
private boolean valid(char[][] chess, int row, int col){
for(int i = 0; i < row; i++){
if(chess[i][col] == 'Q'){
return false;
}
}
for(int i = row - 1, j = col + 1; i >= 0 && j < chess.length; i--, j++){
if(chess[i][j] == 'Q'){
return false;
}
}
for(int i = row - 1, j = col - 1; i >= 0 && j >= 0; i--, j--){
if(chess[i][j] == 'Q'){
return false;
}
}
return true;
}
}
52:N皇后II
77:组合
class Solution {
public List<List<Integer>> combine(int n, int k) {
List<List<Integer>> list = new LinkedList<>();
backtrack(list, n, k, 1, new ArrayList<>());
return list;
}
private void backtrack(List<List<Integer>> list, int n, int k, int start, List<Integer> tempList) {
if (k == 0) {
list.add(new LinkedList<>(tempList));
return;
}
for (int i = start; i <= n - k + 1; i++) {
tempList.add(i);
backtrack(list, n, k - 1, i + 1, tempList);
tempList.remove(tempList.size() - 1);
}
}
}
78:子集
class Solution {
public List<List<Integer>> subsets(int[] nums) {
List<List<Integer>> res = new ArrayList();
back(nums, new ArrayList<>(), 0, res);
return res;
}
private void back(int[] nums, List<Integer> list, int index, List<List<Integer>> res){
res.add(new ArrayList<>(list));
for(int i = index; i < nums.length; i++){
list.add(nums[i]);
back(nums, list, i + 1, res);
list.remove(list.size() - 1);
}
}
}
79:单词搜索
class Solution {
public boolean exist(char[][] board, String word) {
char[] chars = word.toCharArray();
for(int i = 0; i < board.length; i++){
for(int j = 0; j < board[0].length; j++){
if(dfs(board, chars, i, j, 0)){
return true;
}
}
}
return false;
}
private boolean dfs(char[][] board, char[] chars, int i, int j, int index){
if(i >= board.length || i < 0 || j >= board[0].length || j < 0 || board[i][j] != chars[index]){
return false;
}
if(index == chars.length - 1){
return true;
}
char temp = board[i][j];
board[i][j] = '.';
boolean res = dfs(board, chars, i + 1, j, index + 1) || dfs(board, chars, i - 1, j, index + 1) || dfs(board, chars, i, j + 1, index + 1) || dfs(board, chars, i, j - 1, index + 1);
board[i][j] = temp;
return res;
}
}
89:格雷编码
90:子集II
class Solution {
public List<List<Integer>> subsetsWithDup(int[] nums) {
List<List<Integer>> res = new ArrayList<>();
// if(nums == null){
// return res;
// }
int len = nums.length;
res.add(new ArrayList<>());
Arrays.sort(nums);
List<Integer> pathList = new ArrayList<>();
dfs(nums, len, 0, res, pathList);
return res;
}
private void dfs(int[] nums, int len, int idx, List<List<Integer>> res, List<Integer> pathList){
if(idx == len){
return;
}
for(int i = idx; i < len; i++){
if(i > idx && nums[i] == nums[i-1]){
continue;
}
pathList.add(nums[i]);
res.add(new ArrayList<>(pathList));
dfs(nums, len, i+1, res, pathList);
pathList.remove(pathList.size() - 1);
}
}
}
93:复原IP地址
class Solution {
public List<String> restoreIpAddresses(String s) {
List<String> res = new ArrayList<>();
ArrayList<String> pathList = new ArrayList<>();
dfs(s, res, pathList);
return res;
}
private void dfs(String s, List<String> res, ArrayList<String> pathList){
int len = s.length();
if(len == 0){
if(pathList.size() == 4){
res.add(String.join(".", pathList));
}
}
if(pathList.size() == 4){
return;
}
for(int i = 1; i <= len; i++){
if(i > 3){
break;
}
String subStr = s.substring(0, i);
int subLen = subStr.length();
if((subLen == 1) || (subLen == 2 && subStr.charAt(0) != '0') || (subLen == 3 && subStr.charAt(0) != '0' && subStr.compareTo("255") <= 0)){
pathList.add(subStr);
dfs(s.substring(i), res, pathList);
pathList.remove(pathList.size() - 1);
}
}
}
}
95:不同的二叉搜索树II
class Solution {
public List<TreeNode> generateTrees(int n) {
if(n == 0){
return new LinkedList<TreeNode>();
}
return generateTrees(1, n);
}
private List<TreeNode> generateTrees(int start, int end){
List<TreeNode> list = new LinkedList<>();
if(start > end){
list.add(null);
return list;
}
// 回溯法(令根节点值为i)
for(int i = start; i <= end; i++){
//所有可行的左子树集合
List<TreeNode> leftLists = generateTrees(start, i - 1);
//所有可行的右子树集合
List<TreeNode> rightLists = generateTrees(i + 1, end);
for(TreeNode left : leftLists){
for(TreeNode right : rightLists){
TreeNode cur = new TreeNode(i);
cur.left = left;
cur.right = right;
list.add(cur);
}
}
}
return list;
}
}
113:路径总和II
126:单词接龙II
131:分割回文串
class Solution {
public List<List<String>> partition(String s){
List<List<String>> res = new ArrayList<>();
backTrack(s, 0, res, new ArrayList<>());
return res;
}
// 百科踹课(走原路)
private void backTrack(String s, int index, List<List<String>> res, List<String> cur) {
if(index >= s.length()){
res.add(new ArrayList<>(cur));
return;
}
for(int i = index; i < s.length(); i++){
if(!isPalindrome(s, index, i)){
continue;
}
cur.add(s.substring(index, i+1));
backTrack(s, i+1, res, cur);
cur.remove(cur.size() - 1);
}
}
// 派林拽母(回文)
private boolean isPalindrome(String s, int left, int right) {
while(left < right){
if (s.charAt(left++) != s.charAt(right--)){
return false;
}
}
return true;
}
}
140:单词拆分II