难度系数 ⭐⭐⭐难在思路
时间限制 C/C++ 1秒,其他语言2秒 空间限制:C/C++ 32M,其他语言64M
题目内容 输入某二叉树的前序遍历和中序遍历的结果,请重建出该二叉树。假设输入的前序遍历和中序遍历的结果中都不含重复的数字。例如输入前序遍历序列{1,2,4,7,3,5,6,8}和中序遍历序列{4,7,2,1,5,3,8,6},则重建二叉树并返回。
思路 前序遍历的首个节点必然是整颗二叉树的根节点,找到根节点在中序遍历中的位置,其左边的节点都是左子树的节点,右边的节点都是右子树的节点。递归实现其左子树的根节点以及对应左右子树的划分,以及右子树的根节点以及对应左右子树的划分。在每次递归过程中,注意输入的先序遍历序列和中序遍历序列都是新的序列,注意区间划分。
package nowcoder;
import java.util.Arrays;
public class No17 {
public static class Node{
public int value;
public Node left;
public Node right;
public Node(int value){
this.value = value;
}
}
public static Node reConstructBinaryTree(int[] pre, int[] in){
if (pre.length == 0 || in.length == 0) return null;
Node root = new Node(pre[0]);
int rootIndex = 0;
for (int i = 0; i < in.length; i++){
if (in[i] == pre[0]) {
rootIndex = i;
break;
}
}
root.left = reConstructBinaryTree(Arrays.copyOfRange(pre, 1, rootIndex + 1), Arrays.copyOfRange(in, 0, rootIndex));
root.right = reConstructBinaryTree(Arrays.copyOfRange(pre, rootIndex + 1, pre.length), Arrays.copyOfRange(in, rootIndex + 1, in.length));
return root;
}
public static void printTree(Node head) {
System.out.println("Binary Tree:");
printInOrder(head, 0, "H", 17);
System.out.println();
}
public static void printInOrder(Node head, int height, String to, int len) {
if (head == null) {
return;
}
printInOrder(head.right, height + 1, "v", len);
String val = to + head.value + to;
int lenM = val.length();
int lenL = (len - lenM) / 2;
int lenR = len - lenM - lenL;
val = getSpace(lenL) + val + getSpace(lenR);
System.out.println(getSpace(height * len) + val);
printInOrder(head.left, height + 1, "^", len);
}
public static String getSpace(int num) {
String space = " ";
StringBuffer buf = new StringBuffer("");
for (int i = 0; i < num; i++) {
buf.append(space);
}
return buf.toString();
}
public static void main(String[] args){
int[] pre = {1,2,4,7,3,5,6,8};
int[] in = {4,7,2,1,5,3,8,6};
printTree(reConstructBinaryTree(pre, in));
}
}