508.出现次数最多的子树元素和
题目
给你一个二叉树的根结点,请你找出出现次数最多的子树元素和。一个结点的「子树元素和」定义为以该结点为根的二叉树上所有结点的元素之和(包括结点本身)。
你需要返回出现次数最多的子树元素和。如果有多个元素出现的次数相同,返回所有出现次数最多的子树元素和(不限顺序)。
示例 1:
输入:
5
/ \
2 -3
返回 [2, -3, 4],所有的值均只出现一次,以任意顺序返回所有值。
示例 2:
输入:
5
/ \
2 -5
返回 [2],只有 2 出现两次,-5 只出现 1 次。
方法
我们用一个哈希表记录每一个可能的和出现的次数。哈希表的key为所有可能的子树元素和的值,value为该值出现的次数。
在深度优先遍历树的过程中,不仅要计算各个子树的元素和。还要根据计算出来的和值更新哈希表和最多出现的次数。
如果当前和值出现的次数为max,那么将其加入列表res。如果当前和值出现的次数大于max,那么需要先将res清空,再将当前的和值加入。
代码
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38
| class Solution { private Map<Integer, Integer> map = new HashMap<>(); private int max = 0; private List<Integer> res = new ArrayList<>(); public int[] findFrequentTreeSum(TreeNode root) { if(root == null) return new int[0]; valSum(root); int[] result = new int[res.size()]; for(int i = 0; i < res.size(); i++) result[i] = res.get(i); return result; }
public int valSum(TreeNode root){ if(root == null) return 0; int L = valSum(root.left); int R = valSum(root.right); int sum = root.val + L + R; if(!map.containsKey(sum)) map.put(sum, 1); else map.put(sum, map.get(sum) + 1); if(map.get(sum) > max){ res.clear(); res.add(sum); } if(map.get(sum) == max) res.add(sum); max = Math.max(max, map.get(sum)); return sum; } }
|