zoukankan      html  css  js  c++  java
  • 题解 P1030 【求先序排列】

    题解 P1030 【求先序排列】

    旧题新解~

    今天做这个题,发现还是没有AC,于是滚回来用了一大堆数据结构A了这个题目,好像复杂度还挺高......

    #include <iostream>
    #include <cstdio>
    #include <stack>
    #include <cstring>
    #include <map>
    #include <algorithm>
    
    using namespace std;
    char mid[101],late[101];
    int mid_[101],late_[101],len=0;
    struct tree{
    	tree *lson,*rson;
    	int ch;
    }rt_,*rt=&rt_;
    map<int,char>ic;
    map<char,int>ci;
    stack<char>qwq;
    
    void build(int ch,tree *root);
    inline void clear_(tree *root);
    void print1(tree *root);
    
    int main()
    {
    	clear_(rt);
    	scanf("%s%s",mid,late);
    	len=strlen(mid);
    	for (register int i=0;i<len;i++)
    	{
    		ic.insert(make_pair(i+1,mid[i]));
    		ci.insert(make_pair(mid[i],i+1));
    	}
    	for (register int i=0;i<len;i++)
    	{
    		late_[i]=ci[late[i]];
    	}
    	reverse(late_,late_+len);
    	for (register int i=0;i<len;i++)
    	{
    		build(late_[i],rt);
    	}
    	print1(rt);
    	while (!qwq.empty())
    	{
    		putchar(qwq.top());
    		qwq.pop();
    	}
    	return 0;
    }
    void build(int ch,tree *root)
    {
    	if (root->ch==-1||root->ch==ch)//相等或者是新的节点 
    	{
    		root->ch=ch;//直接赋值不多说 
    		return ;
    	}
    	else if (root->ch<ch)//小于建左树 
    	{
    		if (root->lson==NULL)//如果没开点就开点 
    		{
    			root->lson=new tree();
    			clear_(root->lson);
    		}
    		build(ch,root->lson);//递归建左子树 
    	}
    	else //那就只剩下大于咯
    	{
    		if (root->rson==NULL)//如果没开点就开点 
    		{
    			root->rson=new tree();
    			clear_(root->rson);
    		}
    		build(ch,root->rson);//递归建右子树 
    	} 
    }
    inline void clear_(tree *root)
    {
    	root->lson=root->rson=NULL;
    	root->ch=-1;
    }
    void print1(tree *root)//先序排列 
    {
    	if (root->lson!=NULL)print1(root->lson);
    	if (root->rson!=NULL)print1(root->rson);
    	qwq.push(ic[root->ch]);
    }
    

    看看这一长串代码,令人生畏......

    首先把题目摆上......

    题目描述

    给出一棵二叉树的中序与后序排列。求出它的先序排列。(约定树结点用不同的大写字母表示,长度(n≤8))。

    输入输出格式

    输入格式:

    2行,均为大写字母组成的字符串,表示一棵二叉树的中序与后序排列。

    输出格式:

    11行,表示一棵二叉树的先序。

    输入输出样例

    输入样例#1: 输出样例#1:
    BADC
    BDCA
    ABCD

    拿过来一看,不就是模拟吗!

    但是我们将原先的中序和后序都离散化成二叉搜索树(闲得慌????),就变得好理解了许多(中规中蒟)

    原文作者说:

    因为对于二叉搜索树左小右大的原则,其中序遍历即为树中的元素的升序排列。而后序遍历是按先左子右子再根节点的顺序输出

    因此 对于二叉搜索树而言——

    如果按照其后序遍历的颠倒后的顺序插入元素,就可以还原整棵树

    原因是在元素x被插入以前,x的父节点已经插入在树中(后序遍历的颠倒后的顺序),因此x一定会插入到原来的树中的位置上。

    原来如果我们按照颠倒的后序遍历建一个二叉搜索树,然后将输出的字符串存入stack<char>,然后再倒着输出,就完成先序遍历的操作。

    感觉有点迷?不要紧,还有一发。

    Q1:为什么要颠倒插入?

    A:因为后序遍历就是离散化后的从大到小的排序,所以我们将其反转,就可以得到一个先序遍历。按照先序遍历,可以还原整棵树。

    Q2:为什么最后要颠倒输出?

    因为我们得到的是先序遍历的离散化数据,所以答案反而是逆序的字母串。

    Clear?

  • 相关阅读:
    安装lnmp 时如何修改数据库数据存储地址及默认访问地址
    ubuntu 设置root用户密码并实现root用户登录
    解决ubuntu 远程连接问题
    linux 搭建FTP服务器
    PHP 根据ip获取对应的实际地址
    如何发布自己的composer包
    使用composer安装composer包报Your requirements could not be resolved to an installable set of packages
    laravel 框架配置404等异常页面
    使用Xshell登录linux服务器报WARNING! The remote SSH server rejected X11 forwarding request
    IoTSharp 已支持国产松果时序数据库PinusDB
  • 原文地址:https://www.cnblogs.com/jelly123/p/10632179.html
Copyright © 2011-2022 走看看