“mcar:期望<mutable-pair>类型的参数; given()“在成员函数</mutable-pair>中

时间:2013-10-14 22:21:16

标签: list function scheme boolean racket

(define fun3
  (lambda (item list) 
    (cond ((equal? item (car list))) 
          ((fun3 item (cdr list)))
          (else #f))))

如果我输入一个不在列表中的元素,我想知道出了什么问题。它显示错误。--mcar: expects argument of type <mutable-pair>; given ()

2 个答案:

答案 0 :(得分:1)

当您到达列表末尾时会发生什么?像(1 2 3)这样的列表实际上是一系列缺点:

(1 2 3) == (1 . (2 . (3 . ())))

使用.获取car左侧的内容,使用cdr获取右侧的内容。请考虑使用您的代码在4中搜索(1 2 3)时会发生什么:

(define fun3
  (lambda (item list) 
    (cond ((equal? item (car list))) 
          ((fun3 item (cdr list)))
          (else #f))))

最后,您将推算item(仍然)4list(3 . ())的情况。现在,(fun3 item (cdr list))将被调用,然后item将(仍然)为4,但list将为()。您无法拨打(car ()),因为()不是一个缺点。您需要明确检查list是空列表的情况:

(define fun3
  (lambda (item list) 
    (cond ((null? list) <...>)
          ((equal? item (car list))) 
          ((fun3 item (cdr list)))
          (else #f))))

现在,有两点需要注意:

  1. 这可以大大简化。使用一些布尔逻辑,您甚至可以完全摆脱cond(有关如何的一些想法,请参阅Scheme, search if a word is a part of list)。这里的一般观点是你正在做一些类似于C代码的事情

    if ( condition ) {
      return false;
    }
    else {
      return true;
    }
    

    可以大大简化为return !condition;。你看到你的代码是如何相似的吗?特别是,你的第二个案例是(fun3 item (cdr list))。如果是真的,那么你返回true。如果它是假的,那么你转到下一个案例并且......返回false。这意味着您只需返回(fun3 item (cdr list))

  2. 的值即可
  3. 更重要的问题是,您说要检查item是否是列表或其任何子列表的元素,而是您现在的代码(等待修复检查空列表)仅检查item是否是list的成员,而不是其任何子列表。当item不等于(car list)时,可能是因为(car list)是另一个列表,您需要递归到并检查item是否在其中。查看search through nested list in scheme to find a number可能会对您有所帮助,但它不会告诉您完全如何做到这一点。

答案 1 :(得分:0)

如果您在球拍中使用可变列表/对,则必须记住它与常规列表完全独立的数据类型,您使用()语法。 当您通过调用“请求”库来处理可变数据时:     (请求计划/ mpair)
你现在必须切换到使用lib-mcar,mcdr,mpair,mlist,mcons中相应的程序来构造对,谓词等。否则就无法从'mcons'接收和错误。 http://docs.racket-lang.org/reference/mpairs.html