SCHEME:列表中的对象



我有一个如下所述的scheme中的对象列表。如何可能调用对象函数时,例如从列表中取出第一个元素?

(define persons false)
(define length 10)
(let loop ((n 0))
    (if (< n length)
        (begin
            (define newp (make-person))
            (send newp setage (- 50 n))
            (cond
                 ((= n 0)
                        (set! persons (list newp)))
                 (else
                        (set! persons (cons persons newp)))
            )
            (loop (+ n 1))
        )
     )
 )
 (define (firstpersonage)
     (send (car persons) getage)
 )

当调用firstpersonage时,我得到的错误信息是没有这样的方法。是否有办法将第一个对象"cast"为"person"类型?

谢谢!

首先,请务必学会正确缩进Lisp。

第二,您的问题是您决定使用一堆副作用来构建Scheme中的人员列表(因此,您忽略了列表建设)。

在这种情况下我要做的是写

(define persons
  (map (lambda (n)
         (let ((newp (make-person)))
           (send newp setage (- 50 n))
           newp))
       (iota 10)))
(define (firstpersonage)
  (send (car persons) getage))

即定义person为年龄从50岁到41岁依次递减的10人的列表。这样做可以避免许多错误的可能性,包括你刚刚被咬的那个。

如果你绝对、肯定地不能忍受放弃你的set!,错误似乎在

这一行。
(set! persons (cons persons newp))

cons不附加两个列表,它在列表的头部添加一个新元素。例如

(cons 3 (list 2 1)) => (3 2 1)

如果你用相反的方法,你将无法得到你想要的

(cons (list 1 2) 3) => ((1 2) . 3)

你得到错误,因为你使用cons错误的方式;你没有构造一个合适的列表。(cons persons newp)创建了一个新的配对,把人放在car中,把newp放在cdr中,所以当你完成后,personscar中的东西不是那些人-物之一。您可能会发现(cdr persons)是一个人-对象,而您可以很好地执行(send (cdr persons) getage)(cdar persons)(cdaar persons)也是人-物。所以它的有点像是一个列表,只有项目在cdr s中,尾巴在car s中(直到你得到你用(list newp)创建的初始列表,它又反过来了)。

无论如何,如果你把它转换成(cons newp persons),它应该可以工作

最新更新