如何处理在Racket中传递给函数的可变数量的参数? [英] How do I handle a variable number of arguments passed to a function in Racket?

查看:137
本文介绍了如何处理在Racket中传递给函数的可变数量的参数?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我喜欢创建不带参数数量的函数,并能够将它们作为列表处理.当创建二叉树和树时,这对我很有用.我现在将其用于最近邻居算法的变体.但是,我的方法确实很可怕:由于我想不出一种方法来遍历不正确的列表(这很可能是不正确的&简并的),因此我尝试使用各种列表函数将不正确的列表强制转换为列表形式.

I like creating functions which take an unlimited number of arguments, and being able to deal with them as a list. It's been useful to me when creating binary trees & I'm using it for a variation on the nearest-neighbour algorithm right now. My method, however, is really horrible: since I can't think of a way to iterate over an improper list (which may well be improper & degenerate), I tried using various list functions to force the improper list into list form.

这是我最好的尝试,它是通过一个简单的函数来确定地图节点之间的差异(有效,只是不确定为什么会起作用):

This is my best attempt in a simple function to determine difference between map-nodes (works, just not sure why it works):

(define distance-between
  (lambda xs
    (let ([input-list (list* xs null)])
      (letrec ([f (lambda (xs acc)
                    (if (null? (cdr xs))
                        acc
                        (f (cdr xs) (+
                                     (abs (- (map-node-x (car xs)) (map-node-x (cadr xs))))
                                     (abs (- (map-node-y (car xs)) (map-node-y (cadr xs))))
                                     acc))))])                   
       (f (car input-list) 0)))))

如您所见,这是一个丑陋的解决方案,其中涉及一些对我来说似乎很神奇的魔术-当我将不正确的列表包括在列表中时,为什么不当列表会被强制转换为列表形式? (注意:这句话有误导性,不会发生).

As you can see, it's an ugly solution and involves some of what seems like magic to me - why is the improper list coerced into list form when I include it in a list*? (note: this sentence is misleading, this does not occur).

我宁愿有一个不错的解决方案,也不要魔术.有人可以帮忙吗?

I'd rather have a pretty solution and no magic. Can anyone help?

例如,典型的输入为:

(distance-between (map-node 1 2) (map-node 2 3) (map-node 3 4))

具有预期结果:

4

(地图节点(a)与m-n(b)之间的距离为2,再加上地图节点(b)与地图节点(c)之间的距离为2)

(a distance of 2 between map-node (a) and m-n (b), plus a distance of 2 between map-node (b) and map-node (c)).

或者可以简单地输入:

(distance-between (map-node 1 2) (map-node 2 2))

并得到以下答案:

1

如果我在原始输入上尝试执行此操作而没有我的(let([input-list ...])...)语句,则会导致错误,因为(?实际上不确定为什么对这个问题给出了答复)

If I attempted this on the raw input, without my (let ([input-list...])...) statement, it would cause an error as (? not actually sure why given response to this question).

该功能按预期工作.

推荐答案

作为可变参数列表接收的列表没有什么不妥当之处(含义:可变数量的参数).例如:

There's nothing improper about the list received as a variadic argument list (meaning: variable number of arguments). For example:

(define test-list
  (lambda xs
    (length xs))) ; xs is a normal list, use it like any other list

(test-list 1 2 3 4)
=> 4

在上面的示例中,xs参数是普通的普通列表,没有什么不妥当的地方.您可以像遍历任何其他列表一样对其进行迭代.无需car它,它已经是列表了!另外,请注意,可以像这样编写相同的函数:

In the above example, the xs parameter is a normal, plain, vanilla list, there's nothing improper about it. You can iterate over it as you would over any other list. There's no need to car it, it's already a list! Also, notice that the same function can be written like this:

(define (test-list . xs)
  (length xs))   ; xs is a normal list, use it like any other list

仅供参考:不正确的列表是不是以空列表结尾的列表.例如:'(1 2 3 . 4).再次,这不是可变参数列表的外观.

Just for reference: an improper list is one that does not end with the null list. For example: '(1 2 3 . 4). Again, that's not how a variadic argument list looks.

这篇关于如何处理在Racket中传递给函数的可变数量的参数?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆