检查符号列表是否有点符号?

时间:2014-11-18 16:00:54

标签: scheme

我有一个'(x y . rest)形式的列表(具有可选参数数量的lambda形式)。 我需要检查一下是否有这种情况,但我似乎无法检查。我打算做的是搜索.是否是列表的成员。

> (memq '\. '(x y z . rest))
Exception in memq: improper list (x y z . rest)
Type (debug) to enter the debugger.

> (memq . '(x y z . rest))
Exception: invalid syntax (x y z . rest)
Type (debug) to enter the debugger.

> (memv '\. '(x y z \. rest))
(\x2E; rest) ;this worked but my input is of the form '(x y z . rest) and not '(x y z \. rest)

3 个答案:

答案 0 :(得分:1)

列表(x y z . rest) 中有一个点符号。它实际上是一个不正确的列表,这样做:(cons 'x (cons 'y (cons 'z 'rest)))

要测试不正确的列表,您可以执行以下操作:

(define (improper-list? x)
  (cond ((null? x) #f)
        ((pair? x) (improper-list? (cdr x)))
        (else #t)))

答案 1 :(得分:1)

.符号不是列表的一部分,它只是打印improper list的惯例(一个不以空列表结尾的约定)。要测试我们是否有不正确的列表,请使用内置过程尝试:

(define (atom? x)
  (and (not (null? x))
       (not (pair? x))))

(define (improper-list? lst)
  (or (atom? lst)
      (not (list? lst))))

按预期工作:

(improper-list? 1)
=> #t
(improper-list? '())
=> #f
(improper-list? '(1 2 3))
=> #f
(improper-list? '(1 2 . x))
=> #t

答案 2 :(得分:1)

列表中没有元素。相反,它是当列表中的最后一个cdr不是空列表时使用的符号。不过,这也在其他问题中有所描述。例如,请查看Dot notation in scheme

关于检查不正确的列表,其他两个答案是正确的,并采取类似的方法。但是,我认为指定一个正确的列表更清晰,并且它可以更好地定义正确列表?,然后定义不正确的列表?就此而言:

(define (proper-list? x)
  ;; a proper list is either the empty list (), or a pair
  ;; whose cdr is a proper list.
  (or (null? x)
      (and (pair? x)
           (proper-list? (cdr x)))))

(define (improper-list? x)
  ;; an improper list is anything that is not a proper list
  (not (proper-list? x)))