1.Minimum Depth of Binary Tree
// 递归版,时间复杂度O(n),空间复杂度O(logn)
private static int minDepth(TreeNode root) {
if (root == null) return 0;
return Math.min(minDepth(root.left), minDepth(root.right))+1;
}
2.Maximum Depth of Binary Tree
同上,递归版,// 时间复杂度O(n),空间复杂度O(logn)
public int maxDepth(TreeNode root) {
if (root == null) return 0;
return Math.max(maxDepth(root.left), maxDepth(root.right)) + 1;
}
3.Path Sum
return true, as there exist a root-to-leaf path 5->4->11->2 which sum is 22
// 时间复杂度O(n),空间复杂度O(logn)
public boolean hasPathSum(TreeNode root, int sum) {
if (root == null) return false;
if (root.left == null && root.right == null) // leaf
return sum == root.val;
return hasPathSum(root.left, sum - root.val) || hasPathSum(root.right, sum - root.val);
}
4.Path Sum II
同上,返回路径 // 时间复杂度O(n),空间复杂度O(logn)
public List<List<Integer>> pathSum(TreeNode root, int sum) {
List<List<Integer>> result = new ArrayList<>();
ArrayList<Integer> cur = new ArrayList<>(); // 中间结果
pathSum(root, sum, cur, result);
return result;
}
private static void pathSum(TreeNode root, int gap, ArrayList<Integer> cur, List<List<Integer>> result) {
if (root == null) return;
cur.add(root.val);
if (root.left == null && root.right == null) {
if (gap == root.val) { result.add(new ArrayList<>(cur)); }
}
pathSum(root.left, gap - root.val, cur, result);
pathSum(root.right, gap - root.val, cur, result);
cur.remove(cur.size() - 1); //添加的删除了
}
5.Binary Tree Maximum Path Sum
// 时间复杂度O(n),空间复杂度O(logn)
private int max_sum;
private int dfs(TreeNode root) {
if (root == null) return 0;
int l = dfs(root.left);
int r = dfs(root.right);
int sum = root.val;
if (l > 0) sum += l;
if (r > 0) sum += r;
max_sum = Math.max(sum, max_sum);
return Math.max(l, r) > 0 ? Math.max(l, r) + root.val : root.val;
}
6、给一棵二叉树, 找到和为最小的子树, 返回其根节点。
public class Solution {
private TreeNode subtree = null;
private int subtreeSum = Integer.MAX_VALUE;
public TreeNode findSubtree(TreeNode root) {
helper(root);
return subtree;
}
private int helper(TreeNode root) {
if (root == null) {
return 0;
}
int sum = helper(root.left) + helper(root.right) + root.val;
if (sum <= subtreeSum) {
subtreeSum = sum;
subtree = root;
}
return sum;
}
}
7、求从根(root)到叶(leaf)的所有路径
Input:{1,2,3,#,5}
Output:["1->2->5","1->3"]
Explanation:
1
/
2 3
5
public class Solution {
public List<String> binaryTreePaths(TreeNode root) {
List<String> paths = new ArrayList<>();
if (root == null) {
return paths;
}
List<String> leftPaths = binaryTreePaths(root.left);
List<String> rightPaths = binaryTreePaths(root.right);
for (String path : leftPaths) {
paths.add(root.val + "->" + path);
}
for (String path : rightPaths) {
paths.add(root.val + "->" + path);
}
// root is a leaf
if (paths.size() == 0) {
paths.add("" + root.val);
}
return paths;
}
}
8、给定一棵二叉树,找到两个节点的最近公共父节点(LCA)。
最近公共祖先是两个节点的公共的祖先节点且具有最大深度。
public class Solution {
// 在root为根的二叉树中找A,B的LCA:
// 如果找到了就返回这个LCA
// 如果只碰到A,就返回A
// 如果只碰到B,就返回B
// 如果都没有,就返回null
public TreeNode lowestCommonAncestor(TreeNode root, TreeNode node1, TreeNode node2) {
if (root == null || root == node1 || root == node2) {
return root;
}
// Divide
TreeNode left = lowestCommonAncestor(root.left, node1, node2);
TreeNode right = lowestCommonAncestor(root.right, node1, node2);
// Conquer
if (left != null && right != null) {
return root;
}
if (left != null) {
return left;
}
if (right != null) {
return right;
}
return null;
}
}
参考:九章算法
https://www.jiuzhang.com/
https://www.jiuzhang.com/solutions/minimum-subtree/
https://www.jiuzhang.com/solutions/binary-tree-paths/