【发布时间】:2014-03-07 12:22:33
【问题描述】:
我是方案新手,有以下问题: 如果我想让一个函数也打印一个表达式的值,然后调用一个函数,那怎么做呢?
例如,我需要函数foo(n) 来打印n mod 2 的值并调用foo(n/2),我会这样做:
(define foo (lambda (n) (modulo n 2) (foo (/n 2))))
但这当然不会打印n mod 2 的值。
【问题讨论】:
标签: scheme
我是方案新手,有以下问题: 如果我想让一个函数也打印一个表达式的值,然后调用一个函数,那怎么做呢?
例如,我需要函数foo(n) 来打印n mod 2 的值并调用foo(n/2),我会这样做:
(define foo (lambda (n) (modulo n 2) (foo (/n 2))))
但这当然不会打印n mod 2 的值。
【问题讨论】:
标签: scheme
这很简单:
(define foo
(lambda (n)
(display (modulo n 2))
(when (positive? n)
(foo (/ n 2)))))
注意(positive? n)的检查,以确保您永远避免(/ 0 2)。
【讨论】:
我的 Lisp 很糟糕,但这里有一个想法:也许你可以定义一个函数来打印一个值并返回它
(define (debug x) (begin (display x) (newline) x))
然后像这样调用函数
(some-fun (debug (some expression)))
【讨论】:
正如@Juho 所写,您需要添加display。但是,您的过程是递归的,没有基本情况,因此它永远不会终止。
试试这个:
(define foo
(lambda (n)
(cond
((integer? n) (display (modulo n 2))
(newline)
(foo (/ n 2)))
(else n))))
然后
> (foo 120)
0
0
0
1
7 1/2
【讨论】:
通常在处理不止一件事情时,通常会建立列表以在程序完成时提供解决方案。
(define (get-digits number base)
(let loop ((nums '()) (cur number))
(if (zero? cur)
nums
(loop (cons (remainder cur base) nums)
(quotient cur base)))))
(get-digits 1234 10) ; ==> (1 2 3 4)
现在,由于您使用 DrRacket,您有一个调试器,因此您可以实际单步执行此代码,但您应该尝试制作像这样可测试且不会产生副作用的简单位。
当你在谈论粉色和蓝色输出时,我感到很困惑,直到我打开 DrRacket,它确实在那里。粉红色的所有内容都来自程序,蓝色的所有内容通常不会输出,但由于它是 IDE 中顶级表单的结果,REPL 无论如何都会显示它。它们之间的区别在于你不应该在生产代码中依赖蓝色输出。
正如其他人建议的那样,您可以在代码中使用display 进行调试输出。我想告诉你另一种方式。想象一下,我不知道如何处理这些元素,所以我给你机会自己做:
(define (get-digits number base glue)
(let loop ((nums '()) (cur number))
(if (zero? cur)
nums
(loop (glue (remainder cur base) nums)
(quotient cur base)))))
(get-digits 1234 10 cons) ; ==> (1 2 3 4)
(define (debug-glue a d)
(display a)
(newline)
(cons a d))
(get-digits 1234 10 debug-glue) ; ==> (1 2 3 4) and displays "4\n3\n2\n1\n"
【讨论】: