* comparing procedures
@ 2008-01-25 19:39 Gregory Marton
2008-01-26 13:10 ` Neil Jerram
0 siblings, 1 reply; 2+ messages in thread
From: Gregory Marton @ 2008-01-25 19:39 UTC (permalink / raw)
To: bug-guile
Hi folks,
I'm trying to write a meaningful comparison operator for procedures.
Clearly this wants more than procedure-source, because variables in the
source may be bound to different values in the procedure-environment.
I expected something like this to work:
(define foo 3)
(define bar (lambda (x) (+ x foo)))
(define baz (lambda (x) (* x foo)))
(define bar-env (procedure-environment bar))
(define baz-env (procedure-environment baz))
(environment-fold
bar-env
(lambda (sym val so-far)
(and so-far
(environment-bound? baz-env sym)
(equal? val (environment-ref baz-env sym))))
#t)
But it turns out that procedure-environment returns something which is not
something these procedures take as an argument, it's an eval-closure.
(environment? bar-env) ===> #f
(environment? (car bar-env)) ===> #f
I would have thought that this was the wrong procedure but for postings
like this:
http://www.cs.brown.edu/pipermail/plt-scheme/2005-August/009540.html
Could someone point me towards the right way to compare the environment of
a procedure field by field? (Yes, I also have to make sure there are no
extra fields in baz-env too, but that part I'll figure out.)
I did dig a little farther, because I can still do this:
(local-eval 'foo bar-env) ===> 3
and local-eval says:
-- Scheme Procedure: local-eval exp [env]
Evaluate EXP in its environment. If ENV is supplied, it is the
environment in which to evaluate EXP. Otherwise, EXP must be a
memoized code object (in which case, its environment is implicit).
But perhaps not all environments are created equal?
This is in 1.8.1 and 1.8.3.
Thanks, confusedly,
Grem
--
------ __@ Gregory A. Marton http://csail.mit.edu/~gremio/
--- _`\<,_ .
-- (*)/ (*) Contents may have settled out of court.
~~~~~~~~~~~~~~~~-~~~~~~~~_~~~_~~~~~v~~~~^^^^~~~~~--~~~~~~~~~~~~~~~++~~~~~~~
^ permalink raw reply [flat|nested] 2+ messages in thread
* Re: comparing procedures
2008-01-25 19:39 comparing procedures Gregory Marton
@ 2008-01-26 13:10 ` Neil Jerram
0 siblings, 0 replies; 2+ messages in thread
From: Neil Jerram @ 2008-01-26 13:10 UTC (permalink / raw)
To: Gregory Marton; +Cc: bug-guile
Gregory Marton <gremio@csail.mit.edu> writes:
> Hi folks,
>
> I'm trying to write a meaningful comparison operator for
> procedures.
Out of interest, why?
> Clearly this wants more than procedure-source, because
> variables in the source may be bound to different values in the
> procedure-environment.
Assuming that your objective is something like "will calling procedure
A have the same effect as calling procedure B", yes.
> I expected something like this to work:
> (define foo 3)
> (define bar (lambda (x) (+ x foo)))
> (define baz (lambda (x) (* x foo)))
> (define bar-env (procedure-environment bar))
> (define baz-env (procedure-environment baz))
OK up to here.
> (environment-fold
> bar-env
> (lambda (sym val so-far)
> (and so-far
> (environment-bound? baz-env sym)
> (equal? val (environment-ref baz-env sym))))
> #t)
Here is the problem. All of the environment-* procedures are an
experimental thing that actual has no current connection to the rest
of Guile.
> But it turns out that procedure-environment returns something which is
> not something these procedures take as an argument, it's an
> eval-closure.
Yes; an "eval-closure" is Guile's term for the top-level environment
of a module.
If the lambda had been defined in a non-top-level environment
(e.g. within a let), procedure-environment would give you something
like this:
(((a b c) . (3 #f (foo bar baz))) ; innermost lexical env vars
((s t) . ("hi" 23)) ; next outer lexical env vars
...
<eval-closure>) ; top level env
> I would have thought that this was the wrong procedure but for
> postings like this:
> http://www.cs.brown.edu/pipermail/plt-scheme/2005-August/009540.html
Well there's nothing wrong with procedure-environment. Perhaps you
could ask William Josephson if you can use his code?
> Could someone point me towards the right way to compare the
> environment of a procedure field by field? (Yes, I also have to make
> sure there are no extra fields in baz-env too, but that part I'll
> figure out.)
Given the above structure, you could compare the elements of the
list that procedure-environment returns. When you get to comparing
two <eval-closure>s, I think the only sensible thing is to use eq?.
I've appended some code below that I just used to explore this a bit.
> Thanks, confusedly,
> Grem
I'm afraid it is a bit confusing, with the environment-* procs sitting
there. I hope the above has helped.
Regards,
Neil
neil@arudy:~$ guile
guile> (define p (let ((a 1) (b 2)) (lambda () (list 4 5 6))))
guile> p
#<procedure p ()>
guile> (procedure-environment p)
(((b a) 2 1) #<eval-closure b7c238b0>)
guile> (define q (lambda () #t)
)
guile> (procedure-environment q)
(#<eval-closure b7c238b0>)
guile> (define pe (procedure-environment p))
guile> (define qe (procedure-environment q))
guile> (list? pe)
#t
guile> (list? qe)
#t
guile> (list? (car pe))
#t
guile> (list? (car qe))
#f
^ permalink raw reply [flat|nested] 2+ messages in thread
end of thread, other threads:[~2008-01-26 13:10 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2008-01-25 19:39 comparing procedures Gregory Marton
2008-01-26 13:10 ` Neil Jerram
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).