2

「プロシージャreducefと、各キーがリストとペアになっている関連付けのリストであるプロシージャ「reduce-per-key」を定義します。出力は、各キーが結果に関連付けられていることを除いて、同じ構造のリストです関連付けられたリストに reducef を適用する」

私はすでに「map-per-key」と「group-by-key」を書いています:

(define (map-per-key mapf lls)
  (cond
    [(null? lls) '()]
    [else (append (mapf (car lls))(map-per-key mapf (cdr lls)))]))

(define (addval kv lls)
  (cond
    [(null? lls) (list (list (car kv)(cdr kv)))]
    [(eq? (caar lls) (car kv)) 
     (cons (list (car kv) (cons (cadr kv) (cadar lls)))(cdr lls))]
    [else (cons (car lls)(addval kv (cdr lls)))]))

(define (group-by-key lls)
  (cond
    [(null? lls) '()]
    [else (addval (car lls) (group-by-key (cdr lls)))]))

次のステップ 'reduce-per-key' をどのように記述すればよいでしょうか? また、引数が 2 つ必要なのか 3 つ必要なのかを判断するのにも苦労しています。

これまでのところ、私は思いついた:

(define (reduce-per-key reducef lls)
  (let loop ((val (car lls))
             (lls (cdr lls)))
    (if (null? lls) val
        (loop (reducef val (car lls)) (cdr lls)))))

ただし、次のようなテスト ケースを使用します。

(reduce-per-key
   (lambda (kv) (list (car kv) (length (cadr kv))))
   (group-by-key
     (map-per-key (lambda (kv) (list kv kv kv)) xs)))

引数の数が正しくありませんが、引数を 3 つ指定して記述しようとすると、このエラーが発生します。私が間違っていることを知っている人はいますか?

4

1 に答える 1

1

あなたのソリューションは必要以上に複雑で、いくつかのエラーがあります。実際、正しい答えは、新しいヘルパー プロシージャの定義を不要にするほど単純です。空白を埋めるだけで、ソリューションのこのスケルトンに取り組んでみてください。

(define (reduce-per-key reducef lls)
  (if (null? lls)        ; If the association list is empty, we're done
      <???>              ; and we can return the empty list.
      (cons (cons <???>  ; Otherwise, build a new association with the same key 
                  <???>) ; and the result of mapping `reducef` on the key's value
            (reduce-per-key <???> <???>)))) ; pass reducef, advance the recursion

リストに関数をマッピングするための組み込み手続きがあることを思い出してください。次のようにテストします。

(reduce-per-key (lambda (x) (* x x))
                '((x 1 2) (y 3) (z 4 5 6)))

> '((x 1 4) (y 9) (z 16 25 36))

各関連付けは、キー (car部分) とその値としてのリスト(部分) で構成されていることに注意してくださいcdr。例えば:

(define an-association '(x 3 6 9))
(car an-association)
> 'x       ; the key
(cdr an-association)
> '(3 6 9) ; the value, it's a list

最終的な考えとして、この名前reduce-per-keyは少し誤解を招く可能性があります。map-per-keyこの手順は ... を使用して簡単に表現できるため、はるかに適切mapですが、それは読者の演習として残されています。

アップデート:

解決策を見つけたので、次を使用してより簡潔な代替案を提案できますmap

(define (reduce-per-key reducef lls)
  (map (lambda (e) (cons (car e) (map reducef (cdr e))))
       lls))
于 2012-10-09T18:42:25.090 に答える