题目:输入一个表达式。建立一个表达式树。

分析:找到最后计算的运算符(它是整棵表达式树的根),然后递归处理!

            在代码中。仅仅有当p==0的时候。才考虑这个运算符,由于括号中的运算符一定不是最后计算的,应当忽略!

    由于加减跟乘除都是左结合的,最后一个运算符才是最后计算的。所以用两个变量c1跟c2分别记录在括号外面的“最右”出现的加减号和乘除号。

watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvdTAxMDQ3MDk3Mg==/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/SouthEast" alt="" />

#include <iostream>
#include <string>
using namespace std; const int MAXN = 1000;
string str; //表达式
int lch[MAXN], rch[MAXN]; //每一个节点的左右儿子节点编号
char op[MAXN]; //每一个节点里面的字符
int nc = 0; //代表节点个数 int build_tree(string s, int x, int y) {
int p = 0, c1 = -1, c2 = -1; //c1和c2分别记录最右出现的加减号和乘除号,前提是他们在括号外面,由于假设在括号中面的话。这个运算符肯定不是最后一个计算的! int u;
if(y - x == 1) { //假设仅有一个字符。那么建立单独节点! u = ++nc;
lch[u] = 0;
rch[u] = 0;
op[u] = s[x];
return u;
}
for(int i = x; i < y; ++i) { //找括号外面的最右边的加减号跟乘除号。位置分别由c1跟c2记录! switch(s[i]) {
case '(' : ++p; break;
case ')' : --p; break;
case '+' : case '-' : if(!p) {c1 = i; break;} //假设这个 “+” 或者这个 “-” 是在括号外面的! case '*' : case '/' : if(!p) {c2 = i; break;} //假设这个 “*” 或者这个 “/” 是在括号外面的!
}
}
if(c1 < 0) c1 = c2; //假设括号外面没有加减号,那就仅仅能考虑括号外面的乘除号了。 if(c1 < 0) return build_tree(str, x+1, y-1); //假设括号外面加减乘除号都没有,那意思就是整个表达式被一个括号包围了。
u = ++nc;
lch[u] = build_tree(str, x, c1); //运算符s[c1]的左子树区间是[x, c1],右子树区间是[c1+1, y]
rch[u] = build_tree(str, c1+1, y);
op[u] = s[c1];
return u;
} int main() {
cin >> str;
build_tree(str, 0, str.size());
for(int i = 1; i < nc+1; ++i) {
cout << lch[i] << " " << rch[i] << " " << op[i] << endl;
}
return 0;
}

ACM:树的变换,依据表达式建立表达式树的更多相关文章

  1. Java实现后缀表达式建立表达式树

    概述 表达式树的特点:叶节点是操作数,其他节点为操作符.由于一般的操作符都是二元的,所以表达式树一般都是二叉树. 根据后缀表达式"ab+cde+**"建立一颗树 文字描述: 如同后 ...

  2. zoj3299 线段树区间更新,坐标建立线段树的方式

    /* 平台和砖块的坐标离散化,边缘坐标转换成单位长度 处理下落信息,sum数组维护区间的砖块数量 把平台按高度从高到低排序,询问平台区间的砖块有多少,询问后将该区域砖块数置0 */ #include& ...

  3. [.net 面向对象程序设计进阶] (7) Lamda表达式(三) 表达式树高级应用

    [.net 面向对象程序设计进阶] (7) Lamda表达式(三) 表达式树高级应用 本节导读:讨论了表达式树的定义和解析之后,我们知道了表达式树就是并非可执行代码,而是将表达式对象化后的数据结构.是 ...

  4. C#中的Lambda表达式和表达式树

    在C# 2.0中,通过方法组转换和匿名方法,使委托的实现得到了极大的简化.但是,匿名方法仍然有些臃肿,而且当代码中充满了匿名方法的时候,可读性可能就会受到影响.C# 3.0中出现的Lambda表达式在 ...

  5. Lambda表达式和表达式树

    在C# 2.0中,通过方法组转换和匿名方法,使委托的实现得到了极大的简化.但是,匿名方法仍然有些臃肿,而且当代码中充满了匿名方法的时候,可读性可能就会受到影响.C# 3.0中出现的Lambda表达式在 ...

  6. C++ — 后缀表达式转表达式树

    2018-07-21 16:57:26 update 建立表达式树的基本思路:方法类似由下而上建立堆的思想,所以时间复杂度为O(n),这样算法就会变得很简单,只用考虑处理需要入栈的节点和栈中的节点即可 ...

  7. [.net 面向对象程序设计进阶] (6) Lamda表达式(二) 表达式树快速入门

    [.net 面向对象程序设计进阶] (6) Lamda表达式(二) 表达式树快速入门 本节导读: 认识表达式树(Expression Tree),学习使用Lambda创建表达式树,解析表达式树. 学习 ...

  8. 说说lambda表达式与表达式树(未完)

    Lambda表达式可以转换成为代码(委托)或者数据(表达式树).若将其赋值给委托,则Lambda表达式将转换为IL代码:如果赋值给 Expression<TDelegate>,则构造出一颗 ...

  9. 16.C#初见Lambda表达式及表达式树(九章9.1-9.3)

    在说明Lambda相关知识前,我们需要了解Lambda表达式常用于LINQ,那么我们来聊下LINQ. LINQ的基本功能就是创建操作管道,以及这些操作需要的任何状态.这些操作表示了各种关于数据的逻辑: ...

随机推荐

  1. redis键(key)

    redis键: 用于管理redis的键 command key_name > set runoodkey redis OK > del runoodkey 上面的例子中,del是一个命令, ...

  2. css上下左右居中

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  3. float示例

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  4. js数组操作方法

    数组的操作方法在js中可谓是诸子百家,各种某乱的方法让人眼花缭乱,有时候就会分不清什么是自带的什么是曾今写的api了 数组的增删 1 . push() , pop()  和 shift() unshi ...

  5. ORACLE的Copy命令和create table,insert into的比较

    在数据表间复制数据是Oracle DBA经常面对的任务之一,Oracle为这一任务提供了多种解决方案,SQL*Plus Copy 命令便是其中之一.SQL*Plus Copy 命令通过SQL*Net在 ...

  6. netbeans 代码自动补全设置

    编辑器-----代码完成------语言选择"JAVA"------在如图红框中输入 @ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrst ...

  7. Linux下安装jboss并设置自启动服务

    一.JDK和JBOSS下载jdk:https://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.htm ...

  8. TomCat 启动默认加载项目

    在最后加上这句代码即可:<Context path="" docBase="\项目名称" reloadable="true" cros ...

  9. XML解析器之JAXP与DOM4J

    XML是一种数据格式,那么需要对XML文件进行操作就需要用到XML解析器---------针对dom方式和sax方式提供了不同的解析技术-----需要不同的XML解析器 dom方式:会把文档中所有元素 ...

  10. linux-基础-常用命令

    一 Linux的简介 1.1 Linux的概述 Linux是基于Unix的开源免费的操作系统,由于系统的稳定性和安全性几乎成为程序代码运行的最佳系统环境.Linux是由Linus Torvalds(林 ...