tags:

views:

245

answers:

2

I looked for the name of a procedure, which applies a tree structure of procedures to a tree structure of data, yielding a tree structure of results - all three trees having the same structure.

Such a procedure might have the signature:

(map-tree data functree)

Its return value would be the result of elementwise application of functree's elements on the corresponding data elements.

Examples (assuming that the procedure is called map-tree):

Example 1:

(define *2 (lambda (x) (* 2 x)))
; and similar definitions for *3 and *5

(map-tree '(100 (10 1)) '(*2 (*3 *5)))

would yield the result

(200 (30 5))

Example 2:

(map-tree '(((aa . ab) (bb . bc)) (cc . (cd . ce)))
        '((car cdr) cadr))

yields the result

((aa bc) cd)

However I did not find such a function in the SLIB documentation, which I consulted.

Does such a procedure already exist?
If not, what would be a suitable name for the procedure, and how would you order its arguments?

+3  A: 

I don't have a very good name for the function. I'm pasting my implementation below (I've called it map-traversing; others should suggest a better name). I've made the argument order mirror that of map itself.

(define (map-traversing func data)
  (if (list? func)
      (map map-traversing func data)
      (func data)))

Using your sample data, we have:

(map-traversing `((,car ,cdr) ,cadr) '(((aa . ab) (bb . bc)) (cc cd . ce)))

The second sample requires SRFI 26. (Allows writing (cut * 2 <>) instead of (lambda (x) (* 2 x)).)

(map-traversing `(,(cut * 2 <>) (,(cut * 3 <>) ,(cut * 5 <>))) '(100 (10 1)))

The most important thing is that your functions must all be unquoted, unlike your example.

Chris Jester-Young
+1  A: 

I found that with the follwing definition of map-traversing, you don't need to unquote the functions:

(define (map-traversing func data)
  (if (list? func)
      (map map-traversing func data)
      (apply (eval func (interaction-environment)) (list data))))

Note: in my installed version of Guile, due to some reason, only (interaction-environment) does not raise the Unbound variable error. The other environments i.e. (scheme-report-environment 5) and (null-environment 5) raise this error.

Note 2: Subsequently, I found in [1] that for (scheme-report-environment 5) and (null-environment 5) to work, you need first to (use-modules (ice-9 r5rs))

[1]: http://www.mail-archive.com/[email protected]/msg04368.html 'Re: guile -c "(scheme-report-environment 5)" ==> ERROR: Unbound variable: scheme-report-environment'

Omer Zak
True, but then you'd have to use eval, and most Schemers will tell you that normal programs shouldn't use eval.
Chris Jester-Young
Normal programs shouldn't use `eval`.
Nathan Sanders