Racket的相邻差异

时间:2018-02-25 16:05:36

标签: scheme racket

C ++有一个方便的算法std :: adjacent_difference,它计算范围元素的下一个/前一个之间的差异。 Racket实现很简单:

(define (adjacent-difference f lst)
    (if(null? (cdr lst))
       '()
       (cons (f (cadr lst)(car lst))
           (adjacent-difference f (cdr lst)))))

但是我们在Racket中有很多方便的内置算法,所以我想重用它们。 第一个想法是:

(map f (cdr lst) lst)

哎呀,列表的大小不同,我们不能以这种方式使用map。 我可以这样作弊:

(map f (append (cdr lst) '(0)) lst)  ; do not use the last element

但这是一个肮脏的解决方案。 任何想法如何在不编写新函数的情况下完成?

2 个答案:

答案 0 :(得分:2)

这是一个简短的版本:

(define (adjacent-difference f xs)
  (for/list ([x xs] [y (cdr xs)])
    (f y x)))

此处xy运行xs(cdr xs)的元素 在平行下。由于(cdr xs)比循环xs短 当(cdr xs)中没有更多元素时结束。

答案 1 :(得分:0)

如果我理解你想要什么,它不仅是“脏”的,而且它不是一个解决方案,因为在末尾追加零意味着你有比你应该更多的元素。对于三项列表,您应该只有两个不同,对吧?或者你总是想要拉入默认元素?

制作自己的map怎么样?

(define (stalling-map proc . args)
  (if (ormap null? args)
      '()
      (cons (apply proc (map car args))
            (apply stalling-map proc (map cdr args)))))
;;;;
Welcome to DrRacket, version 6.12 [3m].
> (let ((lst '(1 3 7 10 11)))
    (stalling-map - (cdr lst) lst))
'(2 4 3 1)
>