最大树
给出一个没有重复的整数数组,在此数组上建立最大树的定义如下:
- 根是数组中最大的数
- 左子树和右子树元素分别是被父节点元素切分开的子数组中的最大值
利用给定的数组构造最大树。
思路:
对于元素cur,只需求得cur的左边的第一个比它大的数和右边的第一个比它大的数,把cur挂在这两个数中的较小的一个上。最后就一定能够得到一个这样的Max_Tree。
首先需要证明不会出现一个森林。
因为整个数组中元素各不相同,所以按照我们的规则,有且只有一个元素不能挂到其他元素上,所以结果一定构成一棵树,不会是森林。
其次证明都是二叉的,不会出现多余两个的儿子。
我们的规则是压栈的时候,如果当前元素比栈顶元素大,那么就弹出栈中的元素,直到栈为空或者栈顶元素比当前元素大。所以,
我们需要证明任意一个元素最多有一个儿子,可以证明任何一个元素最多有过一个右儿子。
a... b 假设b是a的右儿子,那么a是b的左边第一个比b大的数,a到b的数一定比b小,只有b才有可能为其父亲,b右边的数也只有b才有可能为其父亲。
所以a的单边最多有一个儿子。
1 public TreeNode maxTree(int[] A) { 2 // write your code here 3 if (A == null || A.length == 0) { 4 return null; 5 } 6 Stack<Integer> stack = new Stack<Integer>(); 7 HashMap<Integer,Integer> lessBigMap = new HashMap<Integer,Integer>(); 8 for (int i = 0; i < A.length; i++) { 9 while (!stack.isEmpty() && A[stack.peek()] < A[i]) { 10 popAndSetMap(stack,lessBigMap,A,i); 11 } 12 stack.push(i); 13 } 14 while (!stack.isEmpty()) { 15 popAndSetMap(stack, lessBigMap, A, null); 16 } 17 TreeNode[] nodes = new TreeNode[A.length]; 18 for (int i = 0; i < A.length; i++) { 19 nodes[i] = new TreeNode(A[i]); 20 } 21 TreeNode head = null; 22 for (Map.Entry<Integer, Integer> entry : lessBigMap.entrySet()) { 23 Integer son = entry.getKey(); 24 Integer father = entry.getValue(); 25 if (father != null) { 26 if (father > son) { 27 nodes[father].left = nodes[son]; 28 } 29 else { 30 nodes[father].right = nodes[son]; 31 } 32 } 33 else { 34 head = nodes[son]; 35 } 36 } 37 return head; 38 } 39 public void popAndSetMap(Stack<Integer> stack, Map<Integer,Integer> map, int[] A, Integer r) { 40 int mid = stack.pop(); 41 if (r != null && !stack.isEmpty()) { 42 map.put(mid, A[r] < A[stack.peek()] ? r:stack.peek()); 43 } 44 else if (!stack.isEmpty()) { 45 map.put(mid, stack.peek()); 46 } 47 else { 48 map.put(mid, r); 49 } 50 }
时间: 2024-10-16 06:09:33