用原子计算输入,erlang

Calculate input with atoms, erlang

我正在尝试计算此输入:

evaluate({mul,{plus,{num,2},{num,3}},{num,4}}).

并得到这个作为答案:

20

但我无法让它工作,这是我的代码:

evaluate(List) -> 
[Res] = lists:foldl(fun evaluate/2, [], tuple_to_list(List)),
Res.
evaluate({num,X},Stack) -> [X|Stack];
evaluate(plus,[N1,N2|Stack])->[N1+N2|Stack];
evaluate(mul,[N1,N2|Stack])->[N1*N2|Stack];
evaluate([{Optr, Num1, Num2}],Stack) ->
evaluate(Num1,Stack),evaluate(Num2,Stack),evaluate(Optr,Stack).

能否指出我的错误并指正,谢谢

首先,定义语法:

  • {num,Value} 为数字,
  • {plus,Term1,Term2} 加一个,
  • {mul,Term1,Term2} 乘法,
  • 等等。

二、解决个案:

evaluate({num,Value}) -> Value;
evaluate({plus,Term1,Term2}) -> evaluate(Term1) + evaluate(Term2);
evaluate({mul,Term1,Term2}) -> evaluate(Term1) * evaluate(Term2).

在shell中:

1> E = fun E({num,Value}) -> Value;
1> E({plus,Term1,Term2}) -> E(Term1) + E(Term2);             
1> E({mul,Term1,Term2}) -> E(Term1) * E(Term2)  
1> end.
#Fun<erl_eval.30.90072148>
2> E({mul,{plus,{num,2},{num,3}},{num,4}}).
20
3>

虽然我使用了很多反向抛光符号,但它不适用于您的示例。输入应该是(对于你的例子)[ 2, 3, plus, 4, mul],它可以这样解决:

evaluate(plus,[A,B|Rest]) -> [A+B|Rest];
                             % pop operands,perform  the operation and push the result
evaluate(mul,[A,B|Rest]) -> [A*B|Rest];
evaluate(A,Acc) when is_number(A) -> [A|Acc]. % push operand on the stack

evaluate(Exp) -> [Res] = lists:foldl(evaluate/2,[],Exp), Res.

在shell

22> E = fun E(plus,[A,B|Rest]) -> [A+B|Rest];   
22> E(mul,[A,B|Rest]) -> [A*B|Rest];            
22> E(A,Acc) -> [A|Acc]                         
22> end.                                        
#Fun<erl_eval.36.90072148>
23> Eval = fun(Exp) -> [Res] = lists:foldl(E,[],Exp), Res end.
#Fun<erl_eval.6.90072148>
24> Eval([2,3,plus,4,mul]).                                   
20