Leetcode 513.找树左下角的值
1) 这道题最开始想出来的就是使用BFS,但是DFS更简单
Method 1: BFS 分层遍历每一层,之后拿到最后一层的最左边的节点
class Solution {
public int findBottomLeftValue(TreeNode root) {
if (root == null) {
return -1;
}
if (root.left == null && root.right == null) {
return root.val;
}
Queue<TreeNode> queue = new ArrayDeque<>();
//使用一个变量保存每一层的第一个节点的值
TreeNode last = null;
queue.offer(root);
while (!queue.isEmpty()) {
int size = queue.size();
for (int i = 0; i < size; i++) {
TreeNode node = queue.poll();
if (i == 0) {
last = node;
}
if (node.left != null) {
queue.offer(node.left);
}
if (node.right != null) {
queue.offer(node.right);
}
}
}
return last.val;
}
}
Method 2: 使用DFS
class Solution {
int val = 0;
int maxDepth = 0;
public int findBottomLeftValue(TreeNode root) {
dfs(root, 1);
return val;
}
public void dfs(TreeNode root, int depth) {
//当遍历和记录左孩子节点,返回向上走,遍历右节点时, maxDepth始终大于或者等于depth
//所以val的值不变,除非右节点depth增加
if (root != null) {
if (maxDepth < depth) {
maxDepth = depth;
val = root.val;
}
dfs(root.left, depth + 1);
dfs(root.right, depth + 1);
}
}
}
Leetcode 112. 路径总和
使用递归遍历
class Solution {
boolean res = false;
int currSum = 0;
int target;
public boolean hasPathSum(TreeNode root, int targetSum) {
if (root == null) {
return false;
}
this.target = targetSum;
tranverse(root);
return res;
}
public void tranverse(TreeNode root) {
if (root == null) {
return;
}
//求和
currSum += root.val;
if (root.left == null && root.right == null) {
if (currSum == target) {
res = true;
}
}
//遍历做节点
tranverse(root.left);
tranverse(root.right);
currSum -= root.val;
}
}
Leetcode 113.路径总和ii
class Solution {
List<List<Integer>> res = new ArrayList<>();
public List<List<Integer>> pathSum(TreeNode root, int targetSum) {
if (root == null) {
return res;
}
tranverse(root, targetSum, new ArrayList<>());
return res;
}
public void tranverse(TreeNode root, int targetSum, List<Integer> list) {
if (root == null) {
return;
}
int currSum = targetSum - root.val;
if (root.left == null && root.right == null) {
if (currSum == 0) {
list.add(root.val);
// 这里一定要new ArrayList,浅复制,因为之后list被添加删除,最后结果为空
res.add(new ArrayList<>(list));
list.remove(list.size() - 1);
}
return;
}
list.add(root.val);
tranverse(root.left, currSum, list);
tranverse(root.right, currSum, list);
list.remove(list.size() - 1);
}
}
Leetcode 106.从中序与后序遍历序列构造二叉树
1)通过后序遍历获取根节点
2)可以通过中序遍历确定左子树节点的起始和右子树的起始索引
class Solution {
Map<Integer, Integer> map = new HashMap<>();
public TreeNode buildTree(int[] inorder, int[] postorder) {
if (inorder.length == 1 && postorder.length == 1) {
return new TreeNode(inorder[0]);
}
for (int i = 0; i < inorder.length; i++) {
map.put(inorder[i], i);
}
return buildProcess(inorder, 0, inorder.length - 1,
postorder, 0, postorder.length - 1);
}
public TreeNode buildProcess(int[] inorder, int instart, int intEnd,
int[] postorder, int postStart, int postEnd) {
if (instart > intEnd) {
return null;
}
//get the root and root index
int rootVal = postorder[postEnd];
int rootIndex = map.get(rootVal);
int leftSize = rootIndex - instart;
TreeNode root = new TreeNode(rootVal);
root.left = buildProcess(inorder, instart, rootIndex - 1, postorder, postStart, postStart + leftSize - 1);
root.right = buildProcess(inorder, rootIndex + 1, intEnd, postorder, postStart + leftSize, postEnd - 1);
return root;
}
}
Leetcode 105.从前序与中序遍历序列构造二叉树
1)通过前序遍历获取根节点
2)可以通过中序遍历确定左子树节点的起始和右子树的起始索引
class Solution {
Map<Integer, Integer> map = new HashMap<>();
public TreeNode buildTree(int[] preorder, int[] inorder) {
if (preorder.length == 1) {
return new TreeNode(preorder[0]);
}
for (int i = 0; i < inorder.length; i++) {
map.put(inorder[i], i);
}
return build(preorder, 0, preorder.length - 1, inorder, 0, inorder.length - 1);
}
public TreeNode build(int[] preorder, int prestart, int preend, int[] inorder, int instart, int inend) {
if (prestart > preend || instart > inend) {
return null;
}
int rootVal = preorder[prestart];
int rootIndex = map.get(rootVal);//the root index in inorder
TreeNode root = new TreeNode(rootVal);
int leftSize = rootIndex - instart;
root.left = build(preorder, prestart + 1, prestart + leftSize, inorder, instart, instart + leftSize - 1);
root.right = build(preorder, prestart + leftSize + 1, preend, inorder, rootIndex + 1, inend);
return root;
}
}