zoukankan      html  css  js  c++  java
  • 表达式求值(表达式树)

    一个非常基础的问题,建出表达式树后在树上DP即可。预处理时记录每个位置之前每种符号最近的出现位置可以做到线性,这里直接写了$O(n^2)$算法。

    注意减法和除法不满足交换律所以要取最右边的一个作为当前子树的根,而乘方要取最左边的。以及注意区分减号和负号。

     1 #include<cmath>
     2 #include<cstdio>
     3 #include<cstring>
     4 #include<algorithm>
     5 #define rep(i,l,r) for (int i=(l); i<=(r); i++)
     6 using namespace std;
     7 
     8 const int N=1010;
     9 char s[N],op[N];
    10 double ans,val[N];
    11 int n,rt,top,stk[N],lnk[N],ls[N],rs[N];
    12 
    13 bool isop(char ch){ return ch=='+' || ch=='-' || ch=='*' || ch=='/' || ch=='^'; }
    14 
    15 int build(int l,int r){
    16     if (lnk[l]==r) return build(l+1,r-1);
    17     int rt=0,rt1=0,rt2=0,x=0;
    18     rep(i,l,r){
    19         if (s[i]=='(') i=lnk[i]+1;
    20         if (i>r) break;
    21         if ((s[i]=='+' || s[i]=='-') && (i!=l && !isop(s[i-1]))) rt=i;
    22         if (s[i]=='*' || s[i]=='/') rt1=i;
    23         if (s[i]=='^' && !rt2) rt2=i;
    24     }
    25     if (rt) x=rt; else if (rt1) x=rt1; else x=rt2;
    26     if (!x){ x=r; op[x]='!'; sscanf(s+l,"%lf",&val[x]); return x; }
    27     op[x]=s[x]; ls[x]=build(l,x-1); rs[x]=build(x+1,r); return x;
    28 }
    29 
    30 double dfs(int x){
    31     if (op[x]=='!') return val[x];
    32     double a=dfs(ls[x]),b=dfs(rs[x]),res=0;
    33     if (op[x]=='+') res=a+b;
    34     if (op[x]=='-') res=a-b;
    35     if (op[x]=='*') res=a*b;
    36     if (op[x]=='/') res=a/b;
    37     if (op[x]=='^') res=pow(a,b);
    38     return res;
    39 }
    40 
    41 int main(){
    42     freopen("cal.in","r",stdin);
    43     freopen("cal.out","w",stdout);
    44     scanf("%s",s+1); n=strlen(s+1);
    45     rep(i,1,n){
    46         if (s[i]=='(') stk[++top]=i;
    47         if (s[i]==')') lnk[stk[top]]=i,lnk[i]=stk[top],top--;
    48     }
    49     rt=build(1,n); printf("%.3lf
    ",dfs(rt));
    50     return 0;
    51 }
  • 相关阅读:
    数据库索引详解
    解决Eclipse中DDMS一直打印输出Connection attempts的问题
    发布一个关于SharePoint的管理小工具
    POJ 2895
    POJ 2909
    2020/6/9 [MRCTF2020]hello_world_go
    2020/5/31 [GKCTF2020]Chelly’s identity
    2020/5/30 [FlareOn6]Overlong
    2020/5/28 BUU_[WUSTCTF2020]level4
    2020/5/25 BUU_[WUSTCTF2020]level3
  • 原文地址:https://www.cnblogs.com/HocRiser/p/10465990.html
Copyright © 2011-2022 走看看