/*
表达式树思路
(a+b)*(c*(d+e);
对该树进行后序遍历得到后缀表达式
ab+cde+**;
这里实现的是如何根据一个后缀表达式,构造出其相应的表达式树。
算法思想:其实很简单,主要就是栈的使用。算法时间复杂度是O(n),n是后缀表达式长度。
从前向后依次扫描后缀表达式,如果是操作数就建立一个单节点树,并把其指针压入栈。如果是操作符,则
建立一个以该操作符为根的树,然后从栈中依次弹出两个指针(这2个指针分别指向2个树),作为该树的
左右子树。然后把指向这棵树的指针压入栈。直到扫描完后缀表达式。
最后栈中就会只有一个指针。这个指针指向构造的表达式树的根节点。*/(a+b)*(c*(d+e);
对该树进行后序遍历得到后缀表达式
ab+cde+**;
这里实现的是如何根据一个后缀表达式,构造出其相应的表达式树。
算法思想:其实很简单,主要就是栈的使用。算法时间复杂度是O(n),n是后缀表达式长度。
从前向后依次扫描后缀表达式,如果是操作数就建立一个单节点树,并把其指针压入栈。如果是操作符,则
建立一个以该操作符为根的树,然后从栈中依次弹出两个指针(这2个指针分别指向2个树),作为该树的
左右子树。然后把指向这棵树的指针压入栈。直到扫描完后缀表达式。
最后栈中就会只有一个指针。这个指针指向构造的表达式树的根节点。
#include<stdio.h>
#include<malloc.h>
#include<stdlib.h>
#include<string.h>
#include<stack>
#define N 1000
using namespace std;
char str[N],s[2*N];
typedef struct node//二叉树,节点类型
{
char x[10];
struct node *lchild;
struct node *rchild;
}*linklist;
stack<linklist>ch;//存储节点
stack<char>ca;//存储运算符
stack<double> num;
int top;
int com(char x)
{
switch(x)
{
case ‘+‘ :
case ‘-‘ :return 1;
case ‘*‘ :
case ‘/‘ :return 2;
case ‘(‘ :return 0;
default: return -1;
}
}
void zhuan()
{
while(!ca.empty())
ca.pop();
scanf("%s",str);
top=-1;
int k=strlen(str);
ca.push(‘#‘);
for(int i=0;i<k;i++)
{
if(str[i]>=‘0‘&&str[i]<=‘9‘||str[i]==‘.‘)
{
top++;
s[top]=str[i];
}
else if(str[i]==‘+‘||str[i]==‘-‘||str[i]==‘*‘||str[i]==‘/‘)
{
top++;
s[top]=‘,‘;
if(com(str[i])>com(ca.top())) ca.push(str[i]);
else
{
while(com(ca.top())>=com(str[i]))
{
top++;
s[top]=ca.top();
ca.pop();
top++;
s[top]=‘,‘;
}
ca.push(str[i]);
}
}
else if(str[i]==‘(‘) ca.push(str[i]);
else if(str[i]==‘)‘)
{
while(ca.top()!=‘(‘)
{
top++;
s[top]=‘,‘;
top++;
s[top]=ca.top();
ca.pop();
}
ca.pop();
}
}
while(ca.top()!=‘#‘)
{
top++;
s[top]=‘,‘;
top++;
s[top]=ca.top();
ca.pop();
}
}
linklist cre()//根据后缀式创建二叉树
{
while(!ch.empty())
ch.pop();
for(int i=0;i<=top;i++)
{
if(s[i]==‘+‘||s[i]==‘-‘||s[i]==‘/‘||s[i]==‘*‘)
{
linklist tree;
tree=(linklist)malloc(sizeof(struct node));
tree->x[0]=s[i];
tree->x[1]=‘\0‘;
tree->rchild=ch.top();
ch.pop();
tree->lchild=ch.top();
ch.pop();
ch.push(tree);
i++;
}
else if(s[i]>=‘0‘&&s[i]<=‘9‘)
{
linklist tree;
tree=(linklist)malloc(sizeof(struct node));
tree->lchild=NULL;
tree->rchild=NULL;
int j=0;
char b[10];
while(s[i]!=‘,‘)
{
b[j]=s[i];
j++;
i++;
}
b[j]=‘\0‘;
strcpy(tree->x,b);
ch.push(tree);
}
}
return ch.top();
}
void xtree(linklist head)//前缀式输出
{
if(head)
{
printf("%s ",head->x);
xtree(head->lchild);
xtree(head->rchild);
}
}
void xiao(linklist head)
{
if(head)
{
if(head->lchild) xiao(head->lchild);
if(head->rchild) xiao(head->rchild);
free(head);
}
}
void ji()
{
while(!num.empty())
num.pop();
num.push(‘#‘);
double a1,a2;
char s3[15];
char x;
int k;
for(int i=0;i<=top;i++)
{
x=s[i];
if(x>=‘0‘&&x<=‘9‘)
{
k=0;
while(s[i]!=‘,‘)
{
s3[k]=s[i];
k++;
i++;
}
s3[k]=‘\0‘;
num.push(atof(s3));
}
else
{
switch(x)
{
case ‘+‘:
a1=num.top();
num.pop();
a2=num.top();
num.pop();
num.push(a1+a2);
break;
case ‘-‘:
a1=num.top();
num.pop();
a2=num.top();
num.pop();
num.push(a2-a1);
break;
case ‘*‘:
a1=num.top();
num.pop();
a2=num.top();
num.pop();
num.push(a2*a1);
break;
case ‘/‘:
a1=num.top();
num.pop();
a2=num.top();
num.pop();
num.push(a2/a1);
break;
}
}
}
printf("%.2lf\n",num.top());
}
int main()
{
int m;
scanf("%d",&m);
while(m--)
{
zhuan();
linklist head;
head=cre();
xtree(head);
printf("=\n");
xiao(head);
for(int i=0;i<=top;i++)
{
if(s[i]==‘,‘) printf(" ");
else printf("%c",s[i]);
}
printf(" =\n");
ji();
}
return 0;
}
版权声明:本文为博主原创文章,未经博主允许不得转载。