表达式树的构建

来源:互联网 发布:录播软件 编辑:程序博客网 时间:2024/04/30 06:17

这是在《数据结构与算法分析C语言描述》一书中的一道题目。如果有这本书的朋友可以回翻一下书的第70页。

我这里介绍的方法是我自己写出来的,我个人的一些见解。可能写的不是很好,但是也就当个交流吧!有兴趣的朋友欢迎留言

表达式树这个名词大家伙百度一下就可以知道是什么意思,我在这里不详讲概念了,这一棵树的功能是可以帮你把后缀表达式转换为中缀表达式


例如书本上的例子 ab+cde+**

经过表达式树构建之后在利用中序遍历结果会是 (a + b) * c * (d + e);

而我写的这个程序代码对数字是能够处理正确的,字母就不行,意思是当输入12+345+** 就会出正确的中序表达式结果。如果是ab+cde+** 就不是大家预料中的结果!

有心思的朋友可以自行加上去。在infix_tree()这个函数中修改即可!


在这里我主要和大家讨论一下我的算法思想:

第一步:首先你得把这个后缀表达式存储起来(看上去像是废话,但是思路其实就是这样一点一点来的,勿喷!);

第二步:你得为你这个表达式树构建一个栈结构来对每一次的节点进行压栈,当遇到操作符时才从栈里读取内容。(注:稍后我会把这个栈代码发出来给大家!)

并且读出来时应该把他们都用操作符的那个节点去链接起来成为它的左右儿子。第一个读出来的应该为右儿子,为什么?因为栈的存储顺序的关系!

这里可能会有人问不用栈行不行?  我想告诉你们这个问题我有想过不用栈去实现,但是你得保证你能够处理 cde+**这个类似或者更为复杂的表达式!你要记录

他们的操作符与操作数的位置!

第三步:这颗树构建好之后就要中序遍历,中序遍历不理解的我这里再帮大家重温一下 顺序是 左 -> 中 ->右;


好现在就先上树栈的构建方法:

stack_tree.h 

#define STACK_MAX40000typedef struct TreeNode{char ch;struct TreeNode *left;struct TreeNode *right;} *Tptr;Tptr     tc[ STACK_MAX ];static int STACK_STATE = 0;//栈的储存情况//函数声明int PUSH( const Tptr element ); //int 原因为操作成功返回非0.不成功返回0Tptr TOP( void );int POP( void );int stack_isEmpty( void );int stack_isFull( void );


接下来是

stack_tree.c

#include "tree_stack.h"//PUSHintPUSH( const Tptr element ){if( stack_isFull() )return 0;elsetc[ STACK_STATE++ ] = element;return 1;}//TOPTptrTOP( void ){if( stack_isEmpty() )return 0;elsereturn tc[ STACK_STATE-1 ];}//POPintPOP( void ){if( stack_isEmpty() )return 0;elsetc[ --STACK_STATE ] = 0;return 1;}//stack_isEmptyintstack_isEmpty( void ){return STACK_STATE == 0;}//stack_isFullintstack_isFull( void ){return STACK_STATE == STACK_MAX;}


接着就是

中序表达式的构建过程

#include <stdio.h>#include <stdlib.h>#include "tree_stack.c"//funtion statementTptrinfix_tree( const char *ch );voidtraverse_tree( Tptr root );intmain( void ){Tptr head = NULL;printf("请输入后缀表达式回车键代表输入结束中间不可夹带空格\n");char sufix[4000];scanf("%s",sufix);head = infix_tree(sufix);if( head == NULL ){printf("对不起程序出现错误!自动退出!");return 0;}else{puts("正在遍历已经构造好的树!");traverse_tree( head );}return 0;}Tptrinfix_tree( const char *ch ){Tptr p;while( *ch != '\0' ){//puts("<debug0> OK!!");p = ( Tptr )malloc( sizeof( struct TreeNode ) );//puts("<debug1> OK!!");if( *ch >= '0' && *ch <= '9' ){//puts("<debug2> OK!!");p->ch = *ch;p->left = NULL;p->right = NULL;PUSH( p );}else{//puts("<debug3> OK!!");p->ch = *ch;p->right = TOP();POP(); p->left = TOP();POP();PUSH( p );}ch++;}return p;}voidtraverse_tree( Tptr root ){if( root->ch == '+' )putchar('(');if( root->left != NULL ){//puts("<debug0> OK!!");traverse_tree(root->left);}putchar(root->ch);if( root->right != NULL ){//puts("<debug1> OK!!");traverse_tree( root->right );}if( root->ch == '+' )putchar(')');return ;}


有兴趣继续讨论下去的朋友可以加我的QQ152121114 十年一剑。

欢迎大家提意见,万分感谢!


0 0
原创粉丝点击