SCHEME - printf作为调试技术?

时间:2014-12-19 16:07:22

标签: debugging scheme printf

printf命令是一种尝试调试的合理方式,还是其他技术会更快和/或更精确?

(假设是#39; m使用Racket或其他允许printf的方言)。

1 个答案:

答案 0 :(得分:2)

首先关闭。方案(R7RS,R6RS,R5RS)没有printf。有displaySRFI-28 format。因此,我只会将printf视为打印语句,这可能意味着您只是使用display

正确答案是您的代码应该制作成可以轻松进行单元测试的小程序。如果你这样做,你将永远不需要调试器或再次打印出调试信息。

通常,Scheme使用表达式,只需添加一个print语句而不必在begin中包装它和以下语句并不总是很容易。因此,您可能会在添加时引入错误,更糟糕的是,从代码中删除调试信息。例如。

(if (test arg)
    (call-something (car arg))
    (call-something-else (cdr arg))

那么为了在不改变代码的过程的情况下打印(test arg)的结果需要更改多少,以及在不引入新错误的情况下删除它的容易程度如何?如果我真的想打印调试信息,我会做一个宏:

(define-syntax dbg
  (syntax-rules ()
    ((_ . rest) 
     (let ((expr 'rest)
           (res rest))
       (display (list expr '=> res))
       res))))

现在你可以在{1}}前面加上你要检查的地方:

dbg

想象一下,结果og (if (dbg test arg) (call-something (car arg)) (call-something-else (cdr arg)) (test arg),然后您将5输出,而不会将结果更改为((test arg) => 5)

如果您碰巧使用DrRacket,使用非常好的调试器和宏步进器非常简单。有了它,您只需设置一个断点并向有趣的部分运行,然后逐步查看每个步骤计算的值。可能还有一些其他的IDE,但我停止了我发现球拍。即使在使用DrRacket时,没有任何东西可以阻止您在生产中使用不同的实现,例如Ikarus,前提是您在其中一个Scheme报告中写入而不是特定于实现的内容。

小心!对调试器太熟悉的人倾向于制作看起来更像FORTRAN而不是Scheme的长程序。最好的方法是编写程序,就好像你没有任何调试方法一样,在你觉得需要时使用调试器,如果你发现自己一直在调试器中,重构你的代码。