在Scheme中使用“和”

时间:2010-07-07 17:47:50

标签: scheme racket

嘿,我正在尝试在and语句中使用cond。基本上,我不需要在运行某些代码之前只检查<exp1>是否为真,而是需要Scheme来检查<exp1><exp2>是否为真。我了解(and #t #f)评估为#f(and (= 10 (* 2 5)) #t)评估为#t。不幸的是,Scheme不接受

(and (eqv? (length x) 1) (eqv? (car x) #t))

其中x是一个列表,其第一个元素是一个S表达式,其值为#t#f(事实上,我只想做(and (eqv? (length x) 1) (car x)),但这没效果。)

任何人都可以解释我做错了什么,或者如何解决它?另外,有人知道...在Scheme中的含义,如果有的话?谢谢!

2 个答案:

答案 0 :(得分:3)

“其中x是一个列表,其第一个元素是一个S表达式,其值为#t或#f(事实上,我只想做(和(eqv?(长度x)1)(车x) ),但那没用。“

(car x)的第二种情况下,您只需获取列表中的第一个元素,而不进行评估。

说你的清单x是一个清单((eq? 3 3)),我只是在说些什么。它的长度是1,如果我们评估它的第一个元素评估为#t ,但在这种情况下(car x)检索列表 {{1 },这是一个符号和两个数字的列表。

问题的解决方案是使用(eq? 3 3),如eval,它会评估数据,例如列表。

如果您使用另一个答案中所述的(eval (car x) (null-environment)),只有在您通过评估列表((car x))构建x时,如果列表的第一个元素是thunk,则为nullary,这将起作用。 / p>

在这种情况下,你的第一个元素是一个函数,在没有参数的情况下调用时会产生(list (lambda () #t))

答案 1 :(得分:0)

这很有效     (定义l1'(#t #f #t))

(car l1)
; #t    
(and (car l1) (car (cdr l1)))
; #f

但这不是

(define l2 '((eq? 1 1) (eq? 1 2)))

(car l1)
; '(eq? 1 1)  
(and (car l1) (car (cdr l1)))
; fails

你想做什么?

如果是第二个,则考虑在将表达式输入列表之前对其进行评估,如果可能的话。

或者你可以试试:

(define l3 (list eq? 1 1))

l3
; '(#<procedure:eq?> 1 1)

(apply (car l3) (cdr l3))
; #t