2016-12-14 17 views
0

Когда я использую when в списке, #<void> выходят довольно часто незавершенно. Ниже приведены примеры использования карты и для/list.Как предотвратить void в выводе списка

;; using map  
(define lst '(0 0 0 1 1 1 2 2 2 3 3)) 
    (map (lambda (x) 
      (when (equal? 2 x) 
       x 
       )) 
      lst) 
;; expected => '(2 2 2) 
;; output => '(#<void> #<void> #<void> #<void> #<void> #<void> 
;; 2 2 2 #<void> #<void>) 

;; using for/list 
    (define my-list '(0 0 0 1 2 1 2 2 2)) 
    (for/list ([a (drop-right my-list 1)] 
          [b (cdr lst)] 
          [i (in-naturals)]) 
        (when (> a b) 
        (list a b i))) 
;; expected => '(2 1 4) 
;; output => '(#<void> #<void> #<void> #<void> (2 1 4) #<void> #<void> #<void>) 

Когда я использую if условие вместо этого, у меня нет ничего, чтобы поставить для #false государства. Как предотвратить эти #<void>?

ответ

2

Как Renzo упоминает, вы можете использовать filter если ваша цель на самом деле фильтрации. Тем не менее, стоит также отметить, что вы можете использовать for/list для этого, используя условие #:when в цикле:

(define lst '(0 0 0 1 1 1 2 2 2 3 3)) 
(define my-list '(0 0 0 1 2 1 2 2 2)) 

(for/list ([a (drop-right my-list 1)] 
      [b (cdr lst)] 
      [i (in-naturals)] 
      #:when (> a b)) 
    (list a b i)) 

; => '((2 1 4)) 
3

В этих случаях не следует использовать map или for/list: они применяют ту же операцию к списку объектов и возвращает список, полученный consing все результаты применения. Итак, поскольку when не имеет альтернатив, когда условие ложно, результат равен #<void>.

Используйте предопределенный оператор filter вместо:

(filter (lambda (x) (equal? x 2)) '(0 0 0 1 2 1 2 2 2)) 
;; => '(2 2 2 2)