题目:
Given a binary search tree (BST) with duplicates, find all the mode(s) (the most frequently occurred element) in the given BST.
Assume a BST is defined as follows:
- The left subtree of a node contains only nodes with keys less than or equal to the node's key.
- The right subtree of a node contains only nodes with keys greater than or equal to the node's key.
- Both the left and right subtrees must also be binary search trees.
For example:
Given BST [1,null,2,2]
,
1 2 / 2
return [2]
.
Note: If a tree has more than one mode, you can return them in any order.
Follow up: Could you do that without using any extra space? (Assume that the implicit stack space incurred due to recursion does not count).
链接:https://leetcode.com/problems/find-mode-in-binary-search-tree/#/description
3/30/2017
因为有重复的,所以从左子树和右子树区分并不十分容易,联想到中序遍历是按照顺序的,所以按照中序遍历来。
注意的问题:
1. value的初始化。完全可以设为根节点值,若有左子树则在开始会被赋值,若无左子树也可以直接用于和下面的右子树比较
2. 对iterative的树的遍历不熟悉。
3. 当前值与value不一致时,要判断count和maxCount的比较,但无论怎样最后需要赋值value为新的值,并且,count设为1
4. 最后循环外的比较也是有必要的,否则最大值没有判断是否也是出现频率最高。
1 public class Solution { 2 public int[] findMode(TreeNode root) { 3 if (root == null) return new int[0]; 4 ArrayList<Integer> tmp = new ArrayList<Integer>(); 5 int value = root.val; 6 int count = 0; 7 int maxCount = 0; 8 Stack<TreeNode> stack = new Stack<TreeNode>(); 9 TreeNode node = root; 10 11 while (node != null || !stack.empty()) { 12 while (node != null) { 13 stack.add(node); 14 node = node.left; 15 } 16 node = stack.peek(); 17 stack.pop(); 18 if (value == node.val) { 19 count++; 20 } else { 21 if (count == maxCount) { 22 tmp.add(value); 23 } else if (count > maxCount) { 24 tmp.clear(); 25 tmp.add(value); 26 maxCount = count; 27 } 28 value = node.val; 29 count = 1; 30 } 31 node = node.right; 32 } 33 if (count == maxCount) { 34 tmp.add(value); 35 } else if (count > maxCount) { 36 tmp.clear(); 37 tmp.add(value); 38 } 39 int[] ret = new int[tmp.size()]; 40 for (int i = 0; i < ret.length; i++) { 41 ret[i] = tmp.get(i); 42 } 43 return ret; 44 } 45 }
没有想到不用额外空间的算法, 也许真的recursive也可以做?
看到了别人的算法,就是在inorder基础上,用了morris traversal所以不需要stack(题目中如果用recursive也是可以的,第一个代码块就是),遍历了两遍第一遍计算最大长度,第二遍找到所有最大长度的值
https://discuss.leetcode.com/topic/77335/proper-o-1-space/2
1 public class Solution { 2 3 public int[] findMode(TreeNode root) { 4 inorder(root); 5 modes = new int[modeCount]; 6 modeCount = 0; 7 currCount = 0; 8 inorder(root); 9 return modes; 10 } 11 12 private int currVal; 13 private int currCount = 0; 14 private int maxCount = 0; 15 private int modeCount = 0; 16 17 private int[] modes; 18 19 private void handleValue(int val) { 20 if (val != currVal) { 21 currVal = val; 22 currCount = 0; 23 } 24 currCount++; 25 if (currCount > maxCount) { 26 maxCount = currCount; 27 modeCount = 1; 28 } else if (currCount == maxCount) { 29 if (modes != null) 30 modes[modeCount] = currVal; 31 modeCount++; 32 } 33 } 34 35 private void inorder(TreeNode root) { 36 if (root == null) return; 37 inorder(root.left); 38 handleValue(root.val); 39 inorder(root.right); 40 } 41 }
1 private void inorder(TreeNode root) { 2 TreeNode node = root; 3 while (node != null) { 4 if (node.left == null) { 5 handleValue(node.val); 6 node = node.right; 7 } else { 8 TreeNode prev = node.left; 9 while (prev.right != null && prev.right != node) 10 prev = prev.right; 11 if (prev.right == null) { 12 prev.right = node; 13 node = node.left; 14 } else { 15 prev.right = null; 16 handleValue(node.val); 17 node = node.right; 18 } 19 } 20 } 21 }
更多讨论:https://discuss.leetcode.com/category/650/find-mode-in-binary-search-tree