什么是求和树:二叉树的求和树, 是一颗同样结构的二叉树,其树中的每个节点将包含原始树中的左子树和右子树的和。
二叉树:
求和树:
二叉树给出前序和中序输入,求和树要求中序输出;
所有处理数据不会大于int;
数据范围:二叉树的节点数满足
,节点上的值满足 
2行整数,第1行表示二叉树的前序遍历,第2行表示二叉树的中序遍历,以空格分割
1行整数,表示求和树的中序遍历,以空格分割
10 -2 8 -4 6 7 5 8 -2 -4 10 7 6 5
0 4 0 20 0 12 0
import java.util.*;
public class Main{
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
List<Integer> list = new ArrayList<>();
while(sc.hasNext()){
list.add(sc.nextInt());
}
int[] preOrder = new int[list.size()/2];
int[] inOrder = new int[list.size()/2];
for(int i=0;i<list.size();i++){
if(i < list.size()/2)
preOrder[i] = list.get(i);
else
inOrder[i-list.size()/2] = list.get(i);
}
TreeNode root = createTree(preOrder,0,preOrder.length-1,inOrder,0,inOrder.length-1);
dfs(root);
}
//中序遍历输出结果
public static void dfs(TreeNode root){
if(root == null)
return;
dfs(root.left);
int num = PrintNode(root);
System.out.print(num + " ");
dfs(root.right);
}
//打印节点
public static int PrintNode(TreeNode root){
if(root == null)
return 0;
int Left = 0,Right = 0;
if(root.left != null)
Left = root.left.val;
if(root.right != null)
Right = root.right.val;
return Left + Right + PrintNode(root.left) + PrintNode(root.right);
}
//建树
public static TreeNode createTree(int[] preOrder,int preStart,int preEnd,int[] inOrder,int inStart,int inEnd){
if(preStart > preEnd || inStart > inEnd)
return null;
int target = preOrder[preStart];
TreeNode root = new TreeNode(target);
int index;
for(index=inStart;index<=inEnd;index++)
if(inOrder[index] == target)
break;
int leftLength = index-inStart;
root.left = createTree(preOrder,preStart+1,preStart+leftLength,inOrder,inStart,index-1);
root.right = createTree(preOrder,preStart+leftLength+1,preEnd,inOrder,index+1,inEnd);
return root;
}
}
//构造树
class TreeNode{
int val;
TreeNode left;
TreeNode right;
public TreeNode(int x){val = x;}
} import java.util.*;
public class Main{
static class TreeNode{
TreeNode left=null;
TreeNode right=null;
int val=0;
public TreeNode(int value){
val=value;
}
public void setValue(int value){
val=value;
}
}
public static int found(ArrayList<Integer>list,int value){
for(int i=0;i<list.size();i++){
if(list.get(i)==value) return i;
}
return -1;
}
public static TreeNode build(int step,int start,int end,ArrayList<Integer>preList,ArrayList<Integer>midList){
if(preList.size()==0)return null;
if(preList.size()<=step)return null;
TreeNode node=new TreeNode(preList.get(step));
if(start>=end) return node;
int mid=found(midList,preList.get(step));
node.left=build(step+1,start,mid-1,preList,midList);
node.right=build(step+1+mid-start,mid+1,end,preList,midList);
return node;
}
public static TreeNode buildSum(TreeNode root){
if(root==null) return null;
if(root.left==null&&root.right==null) return new TreeNode(0);
int left=0,right=0;
TreeNode cur=new TreeNode(0);
cur.left=buildSum(root.left);
cur.right=buildSum(root.right);
root.setValue(root.left.val+root.right.val+root.val);
if(cur.left!=null) left=root.left.val;
if(cur.right!=null) right=root.right.val;
cur.setValue(left+right);
return cur;
}
static ArrayList<Integer>res=new ArrayList<>();
public static void print(TreeNode root){
if(root==null) return;
print(root.left);
res.add(root.val);
print(root.right);
}
public static void main(String[] args){
ArrayList<Integer>preList=new ArrayList<>();
ArrayList<Integer>midList=new ArrayList<>();
Scanner scanner=new Scanner(System.in);
String pre="";
if(scanner.hasNextLine()) {
pre = scanner.nextLine();
}
String mid="";
if(scanner.hasNextLine()) {
mid=scanner.nextLine();
}
String[] preStr=pre.split(" ");
String[] midStr=mid.split(" ");
for(int i=0;i<preStr.length;i++){
if(!preStr[i].equals("")) {
preList.add(Integer.parseInt(preStr[i]));
midList.add(Integer.parseInt(midStr[i]));
}
}
TreeNode tree1=build(0,0,preList.size()-1,preList,midList);
TreeNode tree=buildSum(tree1);
print(tree);
if(res.size()!=0){
for(int i=0;i<res.size()-1;i++)
System.out.print(res.get(i)+" ");
System.out.print(res.get(res.size()-1));
}
}
} import java.util.*;
class TreeNode{
int val;
TreeNode left = null;
TreeNode right = null;
TreeNode(int val) {this.val = val;}
}
public class Main{
public static void main(String []args){
Scanner sc = new Scanner(System.in);
while (sc.hasNextLine()){
String[] str1 = sc.nextLine().split(" ");
String[] str2 = sc.nextLine().split(" ");
int[] pre = new int[str1.length];
int[] in = new int[str2.length];
for (int i=0;i<pre.length;i++){
pre[i] = Integer.valueOf(str1[i]);
in[i] = Integer.valueOf(str2[i]);
}
TreeNode root = reCon(pre, in);
root = SumTree(root);
InOrderPrint(root);
}
}
public static void InOrderPrint(TreeNode root){
if (root == null) return;
InOrderPrint(root.left);
System.out.print(root.val+" ");
InOrderPrint(root.right);
}
public static TreeNode reCon(int[] pre, int[] in){
if (pre.length == 0) return null;
TreeNode root = new TreeNode(pre[0]);
for (int i=0;i<in.length;i++)
if (in[i] == pre[0]){
root.left = reCon(Arrays.copyOfRange(pre, 1, i+1), Arrays.copyOfRange(in, 0, i));
root.right = reCon(Arrays.copyOfRange(pre, i+1, pre.length), Arrays.copyOfRange(in, i+1, in.length));
}
return root;
}
public static TreeNode SumTree(TreeNode root){
if (root == null) return root;
TreeNode newroot = new TreeNode(Sum(root)-root.val);
newroot.left = SumTree(root.left);
newroot.right = SumTree(root.right);
return newroot;
}
public static int Sum(TreeNode root){
if (root == null) return 0;
return root.val+Sum(root.left)+Sum(root.right);
}
} import java.util.*;
/*
主要是对于二叉树前序遍历和中序遍历关系转换的理解,对于每个求和节点
脑海中需要构想出空间位置关系
*/
public class Main{
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
String[] str1 = sc.nextLine().trim().split(" ");
String[] str2 = sc.nextLine().trim().split(" ");
int[] prevSeq = new int[str1.length];
int[] inSeq = new int[str2.length];
boolean[] boolArr = new boolean[str1.length];// 布尔型数组,标记已求和的节点
int[] inSeqRes = new int[str1.length]; // 记录中序遍历的结果求和树
for(int i = 0;i < prevSeq.length;i++){
prevSeq[i] = Integer.parseInt(str1[i]);
inSeq[i] = Integer.parseInt(str2[i]);
}
for(int i = 0;i < prevSeq.length;i++){
func(prevSeq[i],inSeq,boolArr,inSeqRes);
}
for(int i: inSeqRes){
System.out.print(i+" ");
}
System.out.println();
}
public static void func(int node, int[] inSeq,boolean[] boolArr, int[] inSeqRes){
int index = -1;// index为在中序遍历中找到的需要求和的节点
for(int i = 0;i < inSeq.length;i++){
if(inSeq[i] == node){
index = i;
boolArr[index] = true;
break;
}
}
if(index == -1)
return;// 没有找到就返回
// 对求和节点的左右子树求和
int sum = 0;
for(int i = 0;i < index;i++){
if(boolArr[i]){
continue;// 对于已经标记的节点(已求和),必定是上层节点,直接跳过
}
sum += inSeq[i];
}
for(int i = index + 1;i < inSeq.length;i++){
if(boolArr[i]){
break;
}
sum += inSeq[i];
}
inSeqRes[index] = sum;
}
} import java.util.*;
public class Main {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
ArrayList<Integer> preorder = new ArrayList<>();
String s = sc.nextLine();
String[] ss = s.split(" ");
for(int i = 0 ; i <ss.length;i++){
preorder.add(Integer.valueOf(ss[i]));
}
ArrayList<Integer> inorder = new ArrayList<>();
s = sc.nextLine();
ss = s.split(" ");
for(int i = 0 ; i <ss.length;i++){
inorder.add(Integer.valueOf(ss[i]));
}
getSumTree(preorder,inorder);
//res = new int[preorder.size()];
System.out.println(getSumTree(preorder,inorder).trim());
}
public static String getSumTree(List<Integer> preorder,List<Integer> inorder){
if(preorder==null||preorder.size()==0)return "";
if(inorder==null||inorder.size()==0)return "";
String res = "";
int root = preorder.get(0);
int root_idx = 0;
for(int i = 0 ; i<inorder.size();i++){
if(inorder.get(i) ==root){
root_idx = i;
break;
}
}
res+= getSum(inorder,root_idx);
//左子树
res = getSumTree(preorder.subList(1,root_idx+1) , inorder.subList(0,root_idx)) +" "+res;
//右子树
res =res + getSumTree(preorder.subList(root_idx+1,preorder.size()) , inorder.subList(root_idx+1,inorder.size()));
return res;
}
private static int getSum(List<Integer> inorder, int root_idx) {
if(inorder==null)return 0 ;
int sum = 0;
for(int i = 0 ; i <root_idx;i++)sum+=inorder.get(i);
for(int i = root_idx+1 ; i <inorder.size();i++)sum+=inorder.get(i);
return sum;
}
} import java.util.Scanner;
public class Main {
public static void main(String[] args){
Scanner sc = new Scanner(System.in);
String[] s = sc.nextLine().split(" "); // 抛弃前序
int n = s.length;
int [] nums = new int[n];
for (int i = 0; i < n; i ++){
nums[i] = sc.nextInt();
}
sum(nums, 0, n-1);
for(int num : nums)
System.out.printf("%d ", num);
}
/**
*
* @param nums 中序遍历
* @param start 起始下标
* @param end 终止下标
*/
public static void sum(int[] nums, int start, int end){
if (start < 0 || end >= nums.length) return;
int mid = start + ((end - start) >> 1);
nums[mid] = 0; // 根结点置为0
if (start == mid) return;
for (int i = start, j = end; i < mid; i ++, j --){
nums[mid] += nums[i] + nums[j];
}
// 递归遍历左右子树
sum(nums, start, mid-1);
sum(nums, mid+1, end);
}
}
//只通过60%,没有考虑到节点重复的情况
import java.util.Scanner;
public class Main{
public static void main(String[] args){
Scanner sc=new Scanner(System.in);
String s1=sc.nextLine();
String s2=sc.nextLine();
String[] str1=s1.split(" ");
String[] str2=s2.split(" ");
int[] preorder=new int[str1.length];
int[] inorder=new int[str2.length];
int n=preorder.length;
for(int i=0;i<preorder.length;i++){
preorder[i]=Integer.parseInt(str1[i]);
inorder[i]=Integer.parseInt(str2[i]);
}
func(preorder,0,n-1,inorder,0,n-1);
for(int i=0;i<n;i++){
System.out.print(inorder[i]);
if(i!=n-1){
System.out.print(" ");
}
}
}
public static void func(int[] preorder,int ps,int pl,int[] inorder,int is,int il){
if(ps==pl){
inorder[is]=0;
return;
}
int rootVal=preorder[ps];
int im=is;
while(im<=il && inorder[im]!=rootVal){
im++;
}
inorder[im]=sum(inorder,is,im-1)+sum(inorder,im+1,il);
func(preorder,ps+1,ps+im-is,inorder,is,im-1);
func(preorder,ps+im-is+1,pl,inorder,im+1,il);
}
public static int sum(int[] inorder,int s,int l){
int sum=0;
for(int i=s;i<=l;i++){
sum+=inorder[i];
}
return sum;
}
}