在LISP中求解中缀算法

时间:2013-09-30 03:20:50

标签: lisp common-lisp infix-notation

(defun solve (L)
    (cond
    ((null L) nil)
    (t(eval (list (car (cdr L)) (car L) (car (cdr (cdr L))))))))    

我的代码是一个简单的评估程序,只要输入类似于'(5 + 4),它就可以正常工作。但是我希望能够解决其他输入,例如'(5 +(3 - 1))'(6 + 5) - (4 / 2)。我的问题显然是如何处理括号。我尝试比较'的文字值((<等于(车辆L)'()(解决(cdr L))),但这只会抛出我所有的从whack中得到的近括号。有没有办法检查原子是否是括号?

1 个答案:

答案 0 :(得分:5)

我希望如果这是一个家庭作业问题,你会看看火星的评论,而不是我的回答。如果你只是拿我的代码,你就不会做得好。另一方面,如果你真正阅读所有内容并真正理解它,那就是它。

像火星说的那样,我们需要递归。这很简单;如果我们有一个号码,请将其归还。

(defun solve (expression)
  (if (atom expression)
      expression
    'havent-dealt-with-this-yet))
[22]> (solve '3)
3

如果我们有一个列表,那就采取第二种方法,假设它是运算符,并按照我们样本中的方式进行评估:

(defun solve (expression)
  (if (atom expression)
      expression
    (eval (list (second expression)
                (first expression)
                (third expression)))))
[25]> (solve 3)
3
[26]> (solve '(3 + 4))
7

冷却。但在这里,我们只是你的原始代码。如果我们有嵌套表达式会发生什么?

[27]> (solve '(3 + (2 * 2)))

*** - EVAL: 2 is not a function name; try using a symbol instead

嗯,这不行。我们不能只假设(first expression) or(第三个表达式)中的任何一个都是值;他们可能是表达自己。但我们需要弄清楚表达式的价值。让我们假设我们有办法获取表达式并找到它的值。然后我们的代码可以是:

(defun solve (expression)
  (if (atom expression)
      expression
    (eval (list (second expression)
                (find-expression-value (first expression))
                (find-expression-value (third expression))))))

等待! solve是一个接受表达式并找到其值的函数!

(defun solve (expression)
  (if (atom expression)
      expression
    (eval (list (second expression)
                (solve (first expression))
                (solve (third expression))))))
[43]> (solve 3)
3
[44]> (solve '(3 + 2))
5
[45]> (solve '((3 + 1) * (6 / 2)))
12

TA-哒!