On Sat, Mar 3, 2012 at 6:53 AM, Peter Bex <address@hidden>
On Fri, Mar 02, 2012 at 06:57:56PM -0700, Matt Welland wrote:Like others have said before, case implicitly quotes its arguments,
> I'm trying to convert a comparison operator to the equivalent text. These
> are not symbols. I think case treats the target list as if it was created
> with a quote: '(>). Thus things are all symbols in the list and the eqv?
> returns false.
> > (case > ((>) "yup")(else "nope"))
> > (cond ((eqv? > >) "yup")(else "nope"))
> The cond does what I need just fine, I just didn't understand why case
> didn't also work.
comparing the input to symbols. Your cond is doing something entirely
different; taking the value of the identifiers and comparing the input to
I think you're perhaps confused about the difference between one of many
> Is there a more schemeish way to convert any of the operators to the text
> (define gt >)
> (op->string gt)
> => ">"
possible textual representations of a program and its semantical meaning.
How is Scheme supposed to know the "canonical" name of a random lambda?
The only way is whatever arbitrarily chosen assignment you've decided on
in your program. Having said that, you can extract the "initial" name
of a procedure, which is the name of the surrounding define when the
lambda was first introduced (or its C name in some cases):
It sounds like the answer I was looking for is that there is no scheme "introspection" that maps a procedure to the bound name. The question was merely academic, the cond is fine. I like the select but prefer not to use it as it may not be available "out of the box" should I ever need to migrate to another scheme.
#;1> (define (bar x) 1)
#;2> (define foo (lambda (y) y))
#;3> (let ((whatever (lambda (z) z)))
;; set! global value
(set! qux whatever))
#;4> (##sys#lambda-info->string (##sys#lambda-info bar))
#;5> (##sys#lambda-info->string (##sys#lambda-info foo))
#;6> (##sys#lambda-info->string (##sys#lambda-info qux))
#;7> (##sys#lambda-info->string (##sys#lambda-info +))
#;8> ;; But look at this:
#;9> (##sys#lambda-info->string (##sys#lambda-info +))
"(numbers#+ . args176)"
As you can see, this "canonical" name isn't something you
can easily influence. Another way to solve this particilar
issue is to make an alist or hash table mapping your desired
canonical names to procedures, and op->string look up names
in this table. A macro might also help in reducing work,
as it allows you to list just the "canonical" names of
procedures once and have it generate a case statement:
((_ name op0 ...)
(define (name op)
((op0) (symbol->string 'op0))
(else (error "unknown operator" op)))))))
#;2> (define-op-converter op->string > < + -)
#;3> (op->string >)
#;4> ;; But there are many limitations:
#;5> (op->string >)
Error: unknown operator: #<procedure (numbers#> x11875 x21876 . xs1877)>
Depending on what exactly you're trying to do in the bigger
picture, perhaps rethinking your approach is a better solution
than trying to work around this.
Thanks for the detailed analysis. I probably should have been clearer, I was merely wondering if there was some slick introspection available in scheme that would make this general and easy. My problem is trivial and the cond solves it just fine. The macro you wrote above is very interesting. Although for the reasons you pointed out I won't be using it I did get to learn something. Thanks to all who replied.
"The process of preparing programs for a digital computer
is especially attractive, not only because it can be economically
and scientifically rewarding, but also because it can be an aesthetic
experience much like composing poetry or music."
-- Donald Knuth