中缀表达式转二叉树

【数据结构学习笔记】——根据中缀表达式构建二叉树并输出 要求输入一个中缀表达式,构造表达式树,以文本方式输出树结构。 输入:例如,输入a+b+c*(d+e) 输出:以缩进表示二叉树的层次,左(根),右(叶),上(右子树),下(左子树) 分析我们有两个核心的问题需要解决,一是如何按照中缀表达式来构建二叉树,二是如何用这种形式进行输出。放码过来postfix.h我们知道由后缀表达式生成二叉树很简单,所以我们需要做的第一步就是讲中缀表达式转换为后缀表达 阅读详情

标准算法

#include<bits/stdc++.h>
using namespace std;

using LL = long long;

class PBTNode {
public:
	PBTNode* l;
	PBTNode* r;

	char op; //保持操作符,操作符为x时,表示数字类型
	LL num;  //保存数字

	PBTNode() {
		l = NULL;
		r = NULL;
	}
};

class PrefixBinaryTree {
private:
	PBTNode* root;

	vector<PBTNode*> token_list;

	stack<PBTNode*>	 st; //符号栈
	vector<PBTNode*> ve; //后缀序列

	int pre_map[256];//符号优先级表

	//判断优先级
	int pre(char c) {
		return pre_map[c];
	}

	//字符串转整型
	LL string_to_num(string s) {
		stringstream ss(s);
		LL v;
		ss >> v;
		return v;
	}

	LL calc_dfs(PBTNode* p) {
		if(p->op == 'x') return p->num;
		
		LL a = calc_dfs(p->l);
		LL b = calc_dfs(p->r);

		if(p->op == '+') return a + b;
		if(p->op == '-') return a - b;
		if(p->op == '*') return a * b;
		if(p->op == '/') return a / b;

		return 0;
	}

public:
	PrefixBinaryTree() {
		memset(pre_map, 0, sizeof(pre_map));
		pre_map['+'] = 1;
		pre_map['-'] = 1;
		pre_map['*'] = 2;
		pre_map['/'] = 2;
	}

	//前缀表达式转换成token列表
	void to_token(string expr) {
		string str_t;
		int n = expr.length();
		int i = 0;

		while(i < n) {
			char x = expr[i];
			if(x == ' ') {
				i++;
			} else if(pre_map[x] > 0 || x == '(' || x == ')') {
				PBTNode* p = new PBTNode;
				p->op = x;
				token_list.push_back(p);
				i++;
			} else if(isdigit(x)) {
				string str_t;
				char y = expr[i];
				while(isdigit(y)) {
					str_t.push_back(y);
					i++;
					y = expr[i];
				}
				PBTNode* p = new PBTNode;
				p->op  = 'x';
				p->num = string_to_num(str_t);
				token_list.push_back(p);
			}
		}
	}

	//打印token列表
	void print_token_list() {
		for(auto p : token_list) {
			if(p->op == 'x') {
				printf("[%lld]", p->num);
			} else {
				printf("[%c]", p->op);
			}
		}
		printf("\n");
	}

	//前缀token列表转后缀序列
	void to_postfix() {
		for(auto p : token_list) {
			if(p->op == 'x') {
				ve.push_back(p);
			} else if(st.empty() || p->op == '(') {
				st.push(p);
			} else if(p->op == ')') {
				while(st.top()->op != '(') {
					ve.push_back(st.top());
					st.pop();
				}
				st.pop();//左括号出栈
			} else {
				//确保符号C比栈下一个优先级高
				while(!st.empty() && pre(p->op) <= pre(st.top()->op)) {
					ve.push_back(st.top());
					st.pop();
				}
				st.push(p);
			}
		}

		while(!st.empty()) {
			ve.push_back(st.top());
			st.pop();
		}
	}

	//得到后缀序列
	string get_postfix() {
		string buf;
		stringstream ss;
		for(auto p : ve) {
			if(p->op == 'x') {
				ss << "[" << p->num << "]";
			} else {
				ss << "[" << p->op << "]";
			}
		}
		ss >> buf;
		return buf;
	}

	//创建表达式二叉树
	void build_tree() {
		stack<PBTNode*> sts;
		for(auto p : ve) {
			if(p->op == 'x') {
				p->l = NULL;
				p->r = NULL;
				sts.push(p);
			} else if(pre_map[p->op] > 0) {
				p->r = sts.top();
				sts.pop();

				p->l = sts.top();
				sts.pop();
				sts.push(p);
			}
		}
		root = sts.top();
	}

	//先序遍历
	void preorder(PBTNode* p) {
		if(p == NULL) return;
		if(p->op == 'x') {
			cout << "[" << p->num << "]";
		} else {
			cout << "[" << p->op << "]";
		}
		preorder(p->l);
		preorder(p->r);
	}

	//先序遍历打印
	void print_preorder() {
		printf("preorder:");
		preorder(root);
		printf("\n");
	}

	int calc() {
		return calc_dfs(root);
	}
};

int main() {
	PrefixBinaryTree x;
	string expr = "2*(36+5)+17/1-4";
	x.to_token(expr);
	x.to_postfix();
	x.build_tree();
	LL v = x.calc();
	
	x.print_token_list();
	string expr_postfix = x.get_postfix();
	cout << expr_postfix << endl;
	x.print_preorder();
	cout << v << endl;
	
	return 0;
}
数据结构复习4.1 后缀表达式转中缀表达式与前缀表达式- 二叉树实现 之前总结了利用栈来将中缀表达式转为后缀与前缀表达式的规则,并且附上了代码。最近复习到了树,正好使用二叉树来实现一下。 表达式树 表达式长成下面这个样子: 下图为: 后缀表达式 :ACB*+D/ 的表达式树。 前缀表达式为:/ + A * C B D 中缀表达式为: A + C * B / D ... 阅读详情

相关推荐

中缀表达式转后缀表达式(二叉树实现)

前言 最近在系统复习刷题单,做到了本应滚瓜烂熟的表达式转换的题,忘记了出栈入栈的规则,调了很久也没有过。 最后怒写了一棵表达式树过了,个人认为这个方法便于记忆,也比较好写。 代码 核心流程就是在区间中寻找最后一个运算的运算符,然后将这个运算符作为根,递归左右区间进行建树,叶子节点全部为操作数。 如果区间内不存在运算符,就一定只有一个数字,读入数字作为叶子节点。 代码:以洛谷P1175为例 #include <bits/stdc++.h> using namespace std; string s

J 1466

中缀式表达式转成二叉树(无论再差,人总归是要往上游的)

如何在转化成二叉树的过程中去掉括号,又如何由二叉树生成中缀式的时候将括号加上。 中缀式转成二叉树,理论山彼此的形式是不唯一的 信息缺失的补全,没有考虑到括号的叠加的,在中序遍历的过程中,将括号全部加上去 中缀式转成二叉树 不同于中缀的两个栈,在上述的题目中,是使用两个的栈,一个是字符站另外一个是保存指向二叉树的树根的指针栈 使用flag来标注括号的层数, 每一个操作数都是叶子节点,操作符是非终端的结点 放入一层左括号,当前的flag层数都要加1 遇到右括号,进行脱括号处理, 主要关注结点的位置信息,位.

Blackoutdragon的博客 4525

AutoDock Vina 对接计算(大批量)

AutoDock Vina是一种用于计算生物分子之间相互作用的计算工具,主要用于蛋白质和小分子(通常是潜在药物分子)之间的对接研究。它可以用于虚拟筛选、药物设计和生物分子结合位点的预测等多个应用领域。

MurphyStar的博客 1万+

C++代码实现中缀表达式转化为二叉树,并实现先序中序后序层次遍历输出

【代码】C++代码实现中缀表达式转化为二叉树,并实现先序中序后序层次遍历输出。

2202_76009199的博客 1318

R语言dlnm包避坑指南:手把手教你配置交叉基矩阵(附温度分层与滞后多项式设置)

本文详细介绍了R语言dlnm包在配置交叉基矩阵时的实用技巧与避坑指南,特别针对温度分层与滞后多项式设置提供了具体参数配置建议。通过解析`crossbasis()`函数的核心参数、温度分析的分层策略以及不同基函数的适用场景,帮助研究者高效构建分布滞后非线性模型,避免常见错误并优化模型性能。

weixin_34094282的博客 399

NXP MCU CAN波特率(位时间)配置详解

1. 概述 本文将会详细讲解如何设置NXP MCU的CAN波特率、位时间、采样点等属性。 波特率即CAN总线传输频率,位时间是波特率的倒数,例如波特率是500K,那么位时间 = 1 / 500000 = 0.000002s = 2000ns。 我们先来看一下S32K144单片机的EB中与CAN总线波特率相关的可配置参数有哪些: ...

weixin_42967006的博客 9690

根据中缀表达式构建二叉树

本文从中缀表达式转后缀表达式开始,循序渐进介绍根据中缀表达式构建二叉树的过程。 中缀表达式转后缀表达式 从左往右遍历中缀表达式,无视空格 遇到操作数直接输出 遇到操作符通过按照以下规则处理: 如果当前操作符优先级大于操作符栈的顶部元素,直接入栈 如果当前操作符优先级小于或等于操作符栈的顶部元素,先将顶部元素出栈再将当前操作符入栈 当前操作符为左括号时直接入栈 当前操作符为右括号时,让栈顶到左...

qq_38555975的博客 1万+

深入解析UE5内存分析:从Memreport到Unreal Insights

本文深入解析了UE5内存分析的两大核心工具:Memreport与Unreal Insights。Memreport提供详细的内存快照,帮助定位UObject等资源的内存占用;而Unreal Insights则能进行实时监控与历史回溯,精准追踪内存泄漏。掌握这两款工具是优化UE5项目性能、确保大型项目稳定运行的必备技能。

lg888的博客 1005

中缀表达式转为二叉树

8-(3+5)*(5-6/2) 怎样把中缀表达式转为二叉树?中缀表达式的括号怎样处理? 一般情况下并不能由一个中缀表达式得到一个唯一的二叉树,但是若由二叉树来表示表达式,叶子节点必须是操作数,非叶子节点是操作符,所以能够确定一个二叉树:转化过程如下: 按照优先级加上括号,得到:( 8 - ( (3 + 5) * ( 5 - (6 / 2) ) ) ) 然后从最外层括号开始,依次

lily854212198的专栏 1万+

Claude Code Router 401错误修复

claude code router配置相关环境变量问题

如沐春风 6357

使用VNC可视化Docker容器

Docker容器可视化

Robert_Q的博客 1万+

C++ 中缀表达式转后缀表达式(两种方式:栈、二叉树)

C++ 中缀表达式转后缀表达式 关于后缀表达式如何计算,这里不做过多叙述。以下提供两种方式供参考,第二个种方式粗略的写了计算方式。 方式一 该方式主要是通过栈的数据结构,规定运算符的优先级进行处理即可。 参考链接:https://blog.youkuaiyun.com/liudongdong19/article/details/80767156 源码(C++) #include <iostream> #include <map> #include <string> #incl

田螺姑娘的博客 3387

曲线最小二乘拟合基础

介绍曲线拟合的最小二乘原理,介绍了常规最小二乘和正交最小二乘算法,最后介绍了MathNet矩阵运算库的基本操作。

yh523的博客 1303

中缀表达式转后缀,并打印二叉树

//--------------------head.h------------------------ #ifndef HEAD #define HEAD class TNode//结点类 { public: char oper; TNode *left; TNode *right; //打印时使用,标记该元素在第s层的第t个位置 int s; in

jessies2012的专栏 1061

数学建模学习(120):使用Python实现基于AHP的供应商选择分析

使用Python实现基于AHP的供应商选择分析

全栈川川 909

LinePhone3.2.7(android端最新版本) sip客户端

SIP客户端For android:LinePhone3.2.7(最新版本),官网地址:http://www.linphone.org/

PAT甲级1130 Infix Expression//中缀表达式二叉树转中缀表达式

Given a syntax tree (binary), you are supposed to output the corresponding infix expression, with parentheses reflecting the precedences of the operators. Input Specification: Each input file contains one test case. For each case, the first line gives a po

冷眼看world的博客 263

文档:亲测可用解决vnc灰屏,黑屏,鼠标大黑叉情况

主要解决vnc-viewer灰屏,黑屏,鼠标大黑叉等现象,详细见文档。

栈应用:中缀表达式转后缀表达式并以二叉树储存

中缀表达式就是我们平时所看到的一般计算表达式,如: ①最简单的: 1 + 1 ②稍微复杂一点的: 8 – ( 3 + 2 * 6 ) / 5 + 4而后缀表达式(也被称为逆波兰式)则是将运算符放在了最后,两个操作数放在前面,以及不需要括号表示运算的优先级, 如: ①1 + 1 对应的就是 1 1 + ②8 – ( 3 + 2 * 6 ) / 5 + 4 对应的就是 8 3 2 6

日复一日,年复一年 3262

win10 跳过U8环境检测的IE WebControls.rar

win10 安装u8的时候 提示IE WebControls 不通过,这个工具可以欺骗u8的检查。 跳过U8环境检测的IE WebControls。提示导入失败后,重新检测通过。

android 蓝牙通讯demo

android 下蓝牙通讯demo,实现了发现蓝牙,使能蓝牙,通过蓝牙发送消息。

【二叉树,树,森林相互转换】和中缀表达式转后缀

对式子中每个算术表达式都加上括号,然后,从内到外,把里面的运算符移到当前层括号右侧外,最后去掉括号即可。二叉树,树,森林相互转换见上方链接。

axyw_的博客 324

【408DS算法题】035进阶-17年真题_二叉树转中缀表达式

请设计一个算法,将给定的表达式树(二叉树)转换为等价的中缀表达式(通过括号反映操作符的计算次序)并输出。 --中序遍历、根节点特殊处理

Made in China 701

中缀表达式求值代码C++

这里写自定义目录标题中缀表达式求值代码C++中缀转后缀算法流程图后缀转二叉树流程图需要注意的点代码 中缀表达式求值代码C++ 中缀表达式求值比较合理的做法是: 中缀转后缀 后缀转二叉树 二叉树求值 中缀转后缀 算法 0:初始化运算符栈 1: 对于数字,直接加入后缀表达式 2:对于运算符,与栈顶运算符判断 栈顶运算符优先级更高,弹出到后缀表达式,回到2 栈顶运算符优先级更低,当前运算符直接压栈 3:对于左括号,压栈 4:对于右括号,弹出到后缀表达式,直到遇到左括号 5:最终结果 流程图

Freeverc的博客 1349

C语言实现后缀表达式转中缀表达式(封装得很好哦~

本题实现了用二叉树实现后缀表达式转换为中缀表达式,代码封装效果很好。这是可以进行优化的点。

hjzts666的博客 752

中缀表达式转后缀表达式---栈--二叉树---四则运算

  我们平常书写的四则运算表达式属于中缀表达式,形式为"9+(3-1)*3+10/2",因为所有的运算符号都在两操作数之间,所以称为中缀表达式。我们使用中缀表达式来计算表达式的值,不过这种形式并不适合计算机求解。接下来,我们将中缀表达式转化为后缀表达式,所谓的后缀表达式就是操作符位于操作数后面的不包含括号的算数表达式,也叫做逆波兰表达式。 1)首先介绍一种人工的转化方法(http://www.c...

weixin_30629977的博客 328

将中缀表达式转换成后缀表达式的三种方 法

1利用栈来实现 2利用语法树 3加括号法 上面的两种方法比较常用,并比较适合解答题的形式,若碰到的 是填空题,很多不太熟练算法的人往往就会轻言放弃(因为不能按 步给分,算半天有可能也得个零分)。在这里,本人提出一种简单的 称之为加括号的方法,它会让你在一些考试中大大受益。不 过,只适合不要求过程的填空、选择题之类。 加括号法就是先将待求的中缀表达式依次排开,再将每 一       步要计算的表达式加上括号,最后将每个运算符移到其所 在括号的外面,这样,从左到右扫描得到的序列去掉括号后就是后缀表达式。 例:将

yinxusen的专栏 3077

算数表达式的存储

• 若优先级小于等于栈顶运算符时,将栈顶运算符弹出并输出;再比较新的栈顶运算符,直到该运算符大于栈顶运算符优先级为止,然 后将该运算符压栈;【2019 统考真题】用有向无环图描述表达式(x+y)((x+y)/x),需要的顶点个数至少是(5)。将栈顶的运算符弹出并输出,直到遇到左括号(出栈,不输出);3. 最后,堆栈顶上的元素就是表达式的结果值。有向无环图表示的表达式,图的形态是不唯一的。2.该运算左边的运算是二叉树的左子树;3.该运算右边的运算是二叉树的右子树。,则把堆栈中存留的运算符一并输出。

码明的博客 729

表达式二叉树(简要)

数据结构课程实验c++表达式二叉树

YUYZHE的博客 1607
上一篇: CSP-J-2022题目及参考代码
下一篇: linux安装nvm
鲲鹏混子鱼
博客等级 码龄9年 81粉丝 47原创
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值