首页 > 试题广场 >

通过先序和中序数组生成后序数组

[编程题]通过先序和中序数组生成后序数组
  • 热度指数:2791 时间限制:C/C++ 2秒,其他语言4秒 空间限制:C/C++ 256M,其他语言512M
  • 算法知识视频讲解
给出一棵二叉树的先序和中序数组,通过这两个数组直接生成正确的后序数组。

输入描述:
第一行一个整数 n,表示二叉树的大小。

第二行 n 个整数 a_i,表示二叉树的先序遍历数组。

第三行 n 个整数 b_i,表示二叉树的中序遍历数组。


输出描述:
输出一行 n 个整数表示二叉树的后序遍历数组。
示例1

输入

3
1 2 3
2 1 3 

输出

2 3 1 

备注:

数据保证合法
import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner input = new Scanner(System.in);
        int N = input.nextInt();
        int[] preorder = new int[N];
        int[] inorder = new int[N];
        for (int i = 0; i < N; i++) {
            preorder[i] = input.nextInt();
        }
        for (int i = 0; i < N; i++) {
            inorder[i] = input.nextInt();
        }
        new Main().buildTree(preorder, inorder);
    }
    Map<Integer, Integer> map = new HashMap<>();
    int[] preorder;
    public void buildTree(int[] preorder, int[] inorder) {
        this.preorder = preorder;
        for (int i = 0; i < inorder.length; i++) {
            map.put(inorder[i], i);
        }
        build(0, preorder.length-1, 0, inorder.length-1);
    }
    private void build(int preStart, int preEnd, int inStart, int inEnd) {
        if (preStart > preEnd || inStart > inEnd) {
            return ;
        }
        int rootVal = preorder[preStart];
        int rootIndex = map.get(rootVal);
        int leftNum = rootIndex - inStart;
        build(preStart+1, preStart+leftNum, inStart, rootIndex-1);
        build(preStart+leftNum+1, preEnd, rootIndex+1, inEnd);
        System.out.print(rootVal + " ");
    }
}

发表于 2020-10-05 17:13:19 回复(0)
建树能够更容易输出,而本题的难点就在于如何根据先序和中序两者进行建树
整体思路使用递归,顺序考察先序序列创建根节点,同时左右向对中序序列进行划分
#include <stdlib.h>
#include <stdbool.h>
typedef struct BTree{
    int num;
    struct BTree *lc,*rc;
}BTree;

int k; //标记下个访问的先序结点位置
void CreateBTree(BTree *T,int ordp[],int ordi[],bool visited[],int locate,int n){
    if (visited[locate] || locate>=n || locate<0)
        return;
    else {
        visited[locate]=true;
        int l;
        //在中序序列中向当前根节点左侧探查,考虑是否生成左子树
        for (l=locate-1; l>=0 && !visited[l]; l--) {
            if (ordi[l]==ordp[k+1]) {
                BTree *t=(BTree*)malloc(sizeof(BTree));
                t->num=ordp[++k];
                t->lc=NULL;
                t->rc=NULL;
                T->lc=t;
                CreateBTree(T->lc, ordp, ordi, visited, l, n);
                break;
            }
        }
        //在中序序列中向当前根节点右侧探查,考虑是否生成右子树
        for (l=locate+1; l<n && !visited[l]; l++) {
            if (ordi[l]==ordp[k+1]) {
                BTree *t=(BTree*)malloc(sizeof(BTree));
                t->num=ordp[++k];
                t->lc=NULL;
                t->rc=NULL;
                T->rc=t;
                CreateBTree(T->rc, ordp, ordi, visited, l, n);
                break;
            }
        }
    }
}

void PostOrdBTree(BTree *T,BTree *root){
    if (!T)
        return;
    PostOrdBTree(T->lc, T);
    PostOrdBTree(T->rc, T);
    printf("%d",T->num);
    if (T!=root)
        printf(" ");
}

int main(){
    int n;
    while (~scanf("%d",&n)) {
        int ordp[10001],ordi[10001]; //先序与中序序列数组
        int root=0,locate=0; //记录二叉树根节点信息
        bool visited[10001];
        memset(visited, false, sizeof(visited));
        for (int i=0; i<n; i++) {
            scanf("%d",&ordp[i]);
            if (i==0)
                root=ordp[i]; //找到二叉树根节点值
        }
        for (int i=0; i<n; i++) {
            scanf("%d",&ordi[i]);
            if (root==ordi[i])
                locate=i; //找到二叉树根节点位置
        }
        BTree *T=(BTree*)malloc(sizeof(BTree));
        T->num=root;
        T->lc=NULL;
        T->rc=NULL;
        k=0;
        CreateBTree(T, ordp, ordi, visited, locate, n);
        PostOrdBTree(T, T);
    }
    return 0;
}

发表于 2020-06-05 21:50:42 回复(0)
不必建树,利用递归即可。
先序NLR,中序LNR,后序LRN。
每次从a数组中得到父结点N,再去b数组中找到,分别把L和R两部分确定,接着输出N。
#include<iostream>
#include<vector>
using namespace std;
void getLRN(vector<int> a, int as, int ae, vector<int>b, int bs, int be) {
    if (as == ae) {
        cout << a[as]<<' ';
        return;
    }
    if (as > ae) return;
    int p = bs;
    while (b[p] != a[as]) p++;
    getLRN(a,as+1,p-bs+as,b,bs,p-1);
    getLRN(a,p-bs+as+1,ae,b,p+1,be);
    cout << a[as]<<' ';
}
int main() {
    int n,x;
    vector<int> a, b;
    cin >> n;
    for (int i = 0; i < n; i++) {
        cin >> x;
        a.push_back(x);
    }
    for (int i = 0; i < n; i++) {
        cin >> x;
        b.push_back(x);
    }
    getLRN(a,0,n-1,b,0,n-1);
    return 0;
}


发表于 2019-10-04 15:16:37 回复(0)
之前有道题是根据前中序数组构建二叉树,只要稍微改进一下代码,就可以完成后序序列的输出。
import java.util.*;
public class Main{
    public static void main(String[] args){
        Scanner sc=new Scanner(System.in);
        int n=sc.nextInt();
        sc.nextLine();
        int[] pre=new int[n];
        int[] me=new int[n];
        for(int i=0;i<n;i++){
            pre[i]=sc.nextInt();
        }
        sc.nextLine();
        for(int i=0;i<n;i++){
            me[i]=sc.nextInt();
        }
        System.out.print(get(pre,me,0,n-1,0,n-1));
    }
     public static int  get(int[] pre,int[] me,int ps,int pe,int ms,int mend){
        if(ps>pe)
            return 0;
        if(ps==pe)//叶子结点
            return pre[ps];
        int index=0;
        for(;index<pre.length;index++){
            if(me[index]==pre[ps])
                break;
        }
        int length=index-ms;
        int left=get(pre,me,ps+1,ps+length,ms,index-1);//左儿子结点
         if(left!=0)
        System.out.print(left+" ");
        int right=get(pre,me,ps+length+1,pe,index+1,mend);//右儿子结点
        if(right!=0)
         System.out.print(right+" ");
      
        return pre[ps];
    }
}
发表于 2019-09-06 16:56:38 回复(0)
先重构二叉树,然后进行后续遍历
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.IOException;
import java.util.Arrays;
import java.util.Stack;

class TreeNode {
    public int val;
    public TreeNode left;
    public TreeNode right;
    public TreeNode(int val) {
        this.val = val;
    }
}

public class Main {
    public static void main(String[] args) throws IOException {
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        int n = Integer.parseInt(br.readLine());
        String[] params = br.readLine().split(" ");
        int[] preOrder = new int[n];
        for(int i = 0; i < n; i++) preOrder[i] = Integer.parseInt(params[i]);
        params = br.readLine().split(" ");
        int[] inOrder = new int[n];
        for(int i = 0; i < n; i++) inOrder[i] = Integer.parseInt(params[i]);
        // 重建二叉树
        TreeNode root = buildTree(preOrder, inOrder);
        // 后续遍历
        Stack<TreeNode> stack1 = new Stack<>();
        Stack<TreeNode> stack2 = new Stack<>();
        stack1.push(root);
        while(!stack1.isEmpty()){
            TreeNode node = stack1.pop();
            stack2.push(node);
            if(node.left != null) stack1.push(node.left);
            if(node.right != null) stack1.push(node.right);
        }
        while(!stack2.isEmpty()) System.out.print(stack2.pop().val + " ");
    }
    
    private static TreeNode buildTree(int[] preOrder, int[] inOrder) {
        if(preOrder.length != inOrder.length || preOrder.length == 0) return null;
        if(preOrder.length == 1){
            return new TreeNode(preOrder[0]);
        }else{
            int rootVal = preOrder[0];
            TreeNode root = new TreeNode(rootVal);
            int idx = indexOf(inOrder, rootVal);
            root.left = buildTree(Arrays.copyOfRange(preOrder, 1, 1 + idx), Arrays.copyOfRange(inOrder, 0, idx));
            root.right = buildTree(Arrays.copyOfRange(preOrder, 1 + idx, preOrder.length), Arrays.copyOfRange(inOrder, idx + 1, inOrder.length));
            return root;
        }
    }
    
    private static int indexOf(int[] arr, int target) {
        int idx = -1;
        for(int i = 0; i < arr.length; i++){
            if(arr[i] == target){
                idx = i;
                break;
            }
        }
        return idx;
    }
}

发表于 2021-11-16 10:56:03 回复(0)
import java.util.*;
public class Main { 
public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int size = Integer.parseInt(scanner.nextLine());
        List<String> pre = Arrays.asList(scanner.nextLine().split(" "));
        List<String> order = Arrays.asList(scanner.nextLine().split(" "));
        List<String> post = new ArrayList<>();
        coverTree(pre, order, post);
        for (String s : post) {
            System.out.print(s+" ");
        }
    }

    private static void coverTree(List<String> pre, List<String> order, List<String> post) {
        if (pre.isEmpty() || order.isEmpty()) {
            return;
        }
        post.add(0, pre.get(0));
        int location = order.indexOf(pre.get(0));
        coverTree(pre.subList(location + 1, pre.size()), order.subList(location + 1, order.size()), post);
        coverTree(pre.subList(1, location + 1), order.subList(0, location), post);
    }
}

发表于 2021-09-26 16:08:37 回复(1)
#include<bits/stdc++.h>
using namespace std;
// 无需建树,直接利用树的性质即可,递归解决
void getPost(vector<int>& pre,vector<int>& in,int pre_s,int pre_e,int in_s,int in_e,vector<int>& ans)
{
    if(pre_s>pre_e) return;
    int root = pre[pre_s];
    int index;
    for(index = in_s;index<=in_e;++index)
        if(in[index]==root)
            break;
   //   根节点
    ans.push_back(root);
    // 处理右子树
    getPost(pre,in,pre_s+(index-in_s)+1,pre_e,index+1,in_e,ans);
    // 处理左子树
    getPost(pre,in,pre_s+1,pre_s+index-in_s,in_s,index-1,ans);

}
int main()
{
    int n;
    cin>>n;
    vector<int>ans;
    vector<int>pre(n);
    vector<int>in(n);

    for(int i=0;i<n;++i)
        cin>>pre[i];
    for(int i=0;i<n;++i)
        cin>>in[i];
    getPost(pre,in,0,n-1,0,n-1,ans);
    for(int i=ans.size()-1;i!=-1;i--)
        cout<<ans[i]<<" ";

    return 0;
}
发表于 2020-02-07 12:29:03 回复(0)
import java.util.ArrayList;
import java.util.Scanner;

public class Main {


    /**
     * res: 存放后续遍历的结果
     */
    public static ArrayList<Integer> res = new ArrayList<>();


    /**
     * 树的结点定义
     */
    public static class Node {
        public int val;
        public Node left;
        public Node right;

        public Node(int val, Node left, Node right) {
            this.val = val;
            this.left = left;
            this.right = right;
        }
    }

    /**
     * 根据先序和中序建树
     * @param pre 先序遍历数组
     * @param in 后序遍历数组
     * @param preL 先序子树左边界
     * @param preR 先序子树右边界
     * @param inL 中序子树左边界
     * @param inR 中序子树有边界
     * @return 子树根节点,最后一次回溯是树的根节点
     */
    public static Node create(int[] pre, int[] in, int preL, int preR, int inL, int inR) {
        if (preL > preR) {
            return null;
        }
        Node node = new Node(pre[preL], null, null);
        // 根据先序和中序确定左右子树的根节点在中序遍历的位置
        int mid;
        for (mid = inL; pre[preL] != in[mid]; mid++);
        // 构建左子树
        node.left = create(pre, in, preL+1, preL+mid-inL, inL, mid-1);
        // 构建右子树
        node.right = create(pre, in, preL+mid-inL+1, preR, mid+1, inR);
        return node;
    }

    // 后序遍历
    public static void postOrder(Node node) {
        if (node != null) {
            postOrder(node.left);
            postOrder(node.right);
            res.add(node.val);
        }
    }

    public static void main(String[] args) {
        Scanner input = new Scanner(System.in);
        int N = input.nextInt();
        int[] pre = new int[N];
        int[] in = new int[N];
        for (int i = 0; i < N; i++) {
            pre[i] = input.nextInt();
        }
        for (int i = 0; i < N; i++) {
            in[i] = input.nextInt();
        }
        Node node = create(pre, in, 0, N-1, 0, N-1);
        postOrder(node);
        for (int i = 0; i < res.size(); i++) {
            System.out.print(res.get(i));
            if (i != res.size()-1) {
                System.out.print(" ");
            }
        }
    }
}

发表于 2020-08-01 21:46:15 回复(0)
import java.util.*;
 
public class Main {
    int index = 0;
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int n = scanner.nextInt();
        int[] pre = new int[n];
        int[] in = new int[n];
        int[] end = new int[n];
        //map存储中序遍历中各结点对应的索引
        Map<Integer,Integer> map = new HashMap<>();
        for(int i=0; i<n; i++)
            pre[i] = scanner.nextInt();
        for(int i=0; i<n; i++){
            in[i] = scanner.nextInt();
            map.put(in[i], i);
        }
        //先将根结点放到最末尾,因为递归遍历左右子树完成后会把根节点返回
        //故在此先将根节点放到正确位置
        end[n-1] = pre[0];
        //递归遍历左右子树
        new Main().endOrder(pre, 0, n-1, in, 0, n-1, end, map);
        //打印后序遍历结果
        for(int x : end)
            System.out.print(x+" ");
    }
    public int endOrder(int[] pre, int preStart, int preEnd, 
                        int[] in, int inStart, int inEnd,
                        int[] end, Map<Integer,Integer> map){
        if(preStart > preEnd)
            return 0;
        //节点只有1个直接返回
        if(preStart == preEnd)
            return pre[preStart];
        //获取前序遍历开始点在中序遍历中的索引
        int k = map.get(pre[preStart]);
        //左子树长度
        int length = k - inStart;
        //递归遍历左子树
        int left = endOrder(pre, preStart+1, preStart+length, in, inStart, k-1, end, map);
        //left不为空即左子树不为空
        if(left != 0)
            end[index++] = left;
        //递归遍历右子树
        int right = endOrder(pre, preStart+length+1, preEnd, in, k+1, inEnd, end, map);
        //right不为空即右子树不为空
        if(right != 0)
            end[index++] = right;
        //遍历结束左右子树后返回根节点
        return pre[preStart];
    }
}

发表于 2022-04-09 11:49:17 回复(0)
这题目leetcode什么水平?hard?
发表于 2021-09-26 22:05:19 回复(0)
#建立后序遍历序列
def getLast(pre, mid):
    #如果只有一个节点
    #直接返回
    if len(pre) <= 1:
        return pre
    #先序遍历的第一个节点是根节点
    root = pre[0]
    #划分左右子树
    index = mid.index(root)
    preLeft = pre[1:index + 1]
    preRight = pre[index + 1:]
    midLeft = mid[:index]
    midRight = mid[index + 1:]
    #后序遍历的顺序是左右根
    return getLast(preLeft, midLeft) + getLast(preRight, midRight) + [root]

if __name__ == '__main__':
    #读入数据
    n = int(input())
    pre = input()
    pre = pre.split()
    mid = input()
    mid = mid.split()
    #建立后序遍历序列
    last = getLast(pre, mid)
    print(' '.join(last))

发表于 2021-08-06 08:57:17 回复(0)
#include <stdio.h>
#include <stdlib.h>

typedef struct {
  int val;
  int l_child, r_child;
} TreeNodeInfo, *INFO;

TreeNodeInfo infos[10010]; // 全局区

int createTree(int* pre, int* inorder, int i, int j, int n) {
  // recursion exit condition
  if (n <= 0) return 0;
  if (n == 1) return *(pre + i);

  int k = j;
  while (*(inorder + k) != *(pre + i)) ++k;
  int l = k - j;
  
  infos[*(pre + i)].l_child = createTree(pre, inorder, i + 1, j, l);
  infos[*(pre + i)].r_child = createTree(pre, inorder, i + 1 + l, k + 1, n - 1 - l);
  return *(pre + i);
}

void postorder(INFO infos, int index) {
  if (!index) return;
  postorder(infos, infos[index].l_child);
  postorder(infos, infos[index].r_child);
  fprintf(stdout, "%d ", index);
}

int main(int argc, char* argv[]) {
  int n;
  fscanf(stdin, "%d", &n);
  
  int i, pre[n], inorder[n];
  for (i = 0; i < n; ++i) fscanf(stdin, "%d", pre + i);
  for (i = 0; i < n; ++i) fscanf(stdin, "%d", inorder + i);
  
  createTree(pre, inorder, 0, 0, n);
  postorder(infos, *pre);
  return 0;
}

发表于 2021-08-03 19:21:10 回复(0)
import java.util.*;

public class Main {
    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        int n = sc.nextInt();
        int[] pre = new int[n];
        int[] in = new int[n];
        for (int i = 0; i < n; i++) {
            pre[i] = sc.nextInt();
        }
        for (int j = 0; j < n; j++) {
            in[j] = sc.nextInt();
        }
        
        int[] res = findPos(pre, in);
        for(int i = 0; i < res.length; i++) {
            System.out.print(res[i] + " ");
        }
    }
    
    //无需一定生成二叉树,只分析数组亦可
    //根据当前的先序和中序数组,设置pos arr中最右边空白位置的数,然后划分
    //出左子树的先序、中序数组,以及右子树的先中序数组。
    //先根据右子树的划分设置好后序数组,再根据左子树的划分,从右往左一次设置pos arr。
    public static int[] findPos(int[] pre, int[] in) {
        if (pre == null || in == null)
            return null;
        int len = pre.length;
        int[] pos = new int[len];
        process(pre, in, 0, len-1, 0, len-1, pos, len-1);
        return pos;
    }
    
    public static int process (int[] pre, int[] in, int preS, 
                                int preE, int inS, int inE, 
                                int[] pos, int index) {
        if (preS > preE)
            return index;
        pos[index--] = pre[preS];
        int mid;
        for(mid = inS; in[mid] != pre[preS]; mid++);
        index = process(pre, in, preS+mid-inS+1, preE, mid+1, inE, pos, index);
        return process(pre, in, preS+1, preS+mid-inS, inS, mid-1, pos, index);
    }
}
发表于 2021-06-21 21:43:33 回复(0)
import java.util.Scanner;
import java.util.Map;
import java.util.HashMap;

public class Main {
    private static int posIndex;
    private static Map<Integer, Integer> map = null;
    private static int[] pos = null;

    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);
        map = new HashMap<>();
        int n = sc.nextInt();
        int[] pre = new int[n];
        int[] in = new int[n];
        for (int i = 0; i < n; i++) {
            pre[i] = sc.nextInt();
        }
        for (int i = 0; i < n; i++) {
            in[i] = sc.nextInt();
            map.put(in[i], i);
        }
        pos = new int[n];
        posIndex = n - 1;
        process(pre, 0, n - 1, in, 0, n - 1);
        for (int i = 0; i < n; i++) {
            if (i != 0) {
                System.out.print(" ");
            }
            System.out.print(pos[i]);
        }
    }

    public static void process(int[] pre, int preL, int preR, int[] in, int inL, int inR) {
        if (preL > preR || inL > inR) {
            return;
        }
        int root = pre[preL];
        pos[posIndex--] = root;
        int k = map.get(root);
        int leftSize = k - inL, rightSize = inR - k;
        process(pre, preL + leftSize + 1, preR, in, k + 1, inR);
        process(pre, preL + 1, preL + leftSize, in, inL, k - 1);
    }
}
发表于 2021-04-27 17:18:33 回复(0)
分享一种非递归的方式,O(n)
#include <iostream>
#include <cstdio>
#include <cstring>
#include <bits/stdc++.h>

using namespace std;

#define maxn 10010
int n;
int in[maxn], pre[maxn], post[maxn], stk[maxn];
bool visited[maxn];

int main(){
    while(~scanf("%d", &n)){
        for(int i = 0; i < n; ++i)
            scanf("%d", &(pre[i]));
        for(int i = 0; i < n; ++i)
            scanf("%d", &(in[i]));
        memset(visited, false, sizeof(bool)*maxn);

        int stkcur = 0, incur = -1, precur = 0, postcur = 0;
        while(precur < n){
            stk[stkcur] = pre[precur];
            visited[pre[precur]] = true;
            ++stkcur, ++precur;

            while(incur+1<n && visited[in[incur+1]]){
                while(stkcur > 0 && stk[stkcur-1] != in[incur+1])
                    post[postcur++] = stk[--stkcur];
                ++incur;
            }
        }
        while(stkcur>0)
            post[postcur++] = stk[--stkcur];

        for(int i = 0; i < postcur; ++i)
            printf(" %d"+!i, post[i]);
        printf("\n");
    }
    return 0;
}


发表于 2020-08-18 22:08:19 回复(0)

利用的是根据前序和中序还原树的思路求解的该问题,从右向左还原后序遍历数组

def setPos(preorder, inorder, posorder, si):
    if len(inorder)==0&nbs***bsp;si < 0:
        return si
    data = preorder[0]
    mid = inorder.index(data)
    posorder[si] = data
    si = si-1
    si = setPos(preorder[mid+1:], inorder[mid+1:], posorder, si)
    si = setPos(preorder[1:mid+1], inorder[0:mid], posorder, si)
    return si

n = int(input())
prorder = list(map(int, input().split()))
inorder = list(map(int, input().split()))

posorder = n*['']
s = setPos(prorder, inorder, posorder, n-1)
for i in range(n):
    print(posorder[i], end=' ')

编辑于 2020-04-24 10:55:33 回复(0)
n=int(input())
preOrder=list(map(int,input().split()))
inOrder=list(map(int,input().split()))

def postOrder(preOrder,inOrder):
    if len(preOrder)==1&nbs***bsp;len(preOrder)==0:
        return preOrder
    ind=inOrder.index(preOrder[0])
    left=postOrder(preOrder[1:1+ind],inOrder[:ind])
    right=postOrder(preOrder[1+ind:],inOrder[ind+1:])
    return left+right+[preOrder[0]]
po=postOrder(preOrder,inOrder)
print(' '.join(map(str,po)))

发表于 2020-04-23 20:45:38 回复(0)
参考前面同学的迭代方法来写的:
#include<iostream>
#include<vector>
#include <algorithm>
using namespace std;

 void getLRN(vector<int>pre,vector<int>mid,int num){
     //根据num值来区分各种特殊情况,比如缺少某些子树
     if(num==1){
         cout<<pre[0]<<" ";
     }else if(num==2){
         if(pre[0]==mid[0])
             cout<<pre[1]<<" "<<pre[0]<<" ";
         else
             cout<<mid[0]<<" "<<mid[1]<<" ";
     }else if(num!=0){
         int root = pre[0];
         int p;
         for(p=0;p<num;p++){
             if(mid[p]==root)
                 break;
         }
         vector<int>pr1,pr2,mid1,mid2;
         if(p>0){
             pr1.assign(pre.begin()+1,pre.begin()+p+1);
             mid1.assign(mid.begin(),mid.begin()+p+1);
         }
         if(num-p-1>0){
             pr2.assign(pre.begin()+p+1,pre.begin()+num);
             mid2.assign(mid.begin()+p+1,mid.begin()+num);
         }
         getLRN(pr1,mid1,p);
         getLRN(pr2,mid2,num-p-1);
         cout<<pre[0]<<" ";
     }
 }

 int main(){
     int num;
     cin>>num;
     vector<int>pre;
     vector<int>mid;
     for(int i=0;i<num;i++){
         int data1;
         cin>>data1;
         pre.push_back(data1);
     }
     for(int j=0;j<num;j++){
         int data2;
         cin>>data2;
         mid.push_back(data2);
     }
     getLRN(pre,mid,num);
     return 0;
 }


发表于 2020-02-04 21:25:50 回复(0)
import java.util.*;

public class Main {
	static int[] preArr;
	static int[] inArr;
	static int[] arr;
	static Map<Integer, Integer> map;
	public static void main(String[] args) {
		Scanner scanner = new Scanner(System.in);
		int n = scanner.nextInt();
        preArr = new int[n];
        inArr = new int[n];
        for(int i=0;i<n;i++){
        	preArr[i] = scanner.nextInt();
        }
         map = new HashMap<Integer, Integer>();
        for(int i=0;i<n;i++){
        	inArr[i] = scanner.nextInt();
        	map.put(inArr[i], i);
        }
        arr = new int[n];
        setArr(0, n-1, 0, n-1, n-1);
        for(int i=0;i<n;i++) {
        	System.out.print(arr[i]+" ");
        }
	}
	
	static  int setArr(int preStart,int preEnd,int inStart,int inEnd,int postIndex) {
		if(preStart>preEnd) return postIndex;
		
		arr[postIndex--] = preArr[preStart];
		int index = map.get(preArr[preStart]);
		
		postIndex = setArr(index - inStart + preStart +1 , preEnd, index+1,inEnd,postIndex);
		return setArr(preStart+1,index - inStart + preStart ,inStart,index-1 ,postIndex);
	}

}

发表于 2019-10-29 15:13:32 回复(0)