Just an example where both source text and the compiled code are relevant:

On some occasions I have fallen in the temptation of using eval.
For example I had a metacircular interpreter. In order to check that the
interpreter is metacurcular indeed, I need both the source text (a sexpr)
and the interpeter itself (a procedure). I was tempted to do this as
follows:

#lang racket
(define source-text (quote (a big sexpr)))
(define interpreter
 (let ((ns (make-base-namespace)))
  (parameterize ((current-namespace ns))
   (namespace-require 'racket))
  (eval source-code ns)))
(provide source-text interpeter)

Where the interpeter is a procedure accepting a sexpr and evaluates it in
its own internally defined top-level environment. For example:

(interpreter (quote (add1 3))) -> 4

But it can be done as well, may be better, without eval:

#lang racket
(define-syntax (source/value stx)
 ((_ source-text)
  (syntax (values (quote source-text) source-text))))

(define-values (source-text interpreter)
 (source/value
  (a big sexpr)))

Now let the interpreter use its own source text to test metacircularity.
(interpreter (quasiquote ((unquote source-text) (quote some-sexpr))))

The solution without eval allows use of DrRacket's debug in order to debug
the interpreter. With the solution using eval, DrRacket's debug does
nothing.
There are more ways to do the same, for example by defining the interpreter
in a separate file and using read to extract the source text from that file.

PS: There is a lot more about testing metacircularity, but that is off topic
here.

Jos Koot







-----Original Message-----
From: racket-users@googlegroups.com [mailto:racket-users@googlegroups.com]
On Behalf Of Neil Van Dyke
Sent: martes, 04 de agosto de 2015 19:59
To: Sean Kanaley; Alexis King
Cc: Michael Titke; racket users
Subject: Re: [racket-users] eval PSA (was Sending Closures to Places)

Sean Kanaley wrote on 08/04/2015 12:04 PM:
> " I cannot think of any good uses for eval in Racket."
>
> Any time the mental time spent using eval (or defmacro) is less than 
> that of figuring out how to not use eval or defmacro by using 
> let-parameterize-syntax-splicing-local-transformer-binding-apply-values
instead, 
> which for the average programmer is probably always.

I think maintainability is relevant here.

Just for the list: maintainability is a constant concern for most 
software engineering activity, for very practical, nonreligious, 
reasons.  Maintainability is not just about whether the next programmer 
to come along will be able to read the code.  It's about how easily and 
effectively you and your team can evolve the system over time, whether 
you can actually ever make a complex thing viable, whether and how often 
you get into debugging nightmares or failures, etc.  Unless you're able 
to IPO or job-hop very early in a system lifecycle (and are a bad 
person), developing with maintainability as a consideration should be 
very important to you, for very practical reasons.  That doesn't mean 
maintainability doesn't get traded off appropriately at times, but it 
should be a conscious and informed decision.

> Programming in perfect Racket (or any language) is like finding the 
> optimal solution to the traveling salesman, or finding a large prime 
> with 100% certainty. You are spending disproportionate efforts for the 
> ~same result.

Very little code is purist-perfect, and that's OK.

You might be able to find an academic purist who'd say, "don't use eval, 
because blah blah blah denotational semantics blah blah blah my 
dissertation blah blah blah".  But I think you'll have an easier time 
finding practical expert practitioners who'd tell a newbie, "don't use 
eval, because it's usually a clusterfudge, for no good reason."

If asked about a particular use of eval, a good practical expert 
practitioner should give thoughtful and nuanced consideration, not cling 
to "don't use eval" like an unthinking devotee.  But for broadcasting 
general advice to newbies/students, I think the default practice of 
saying "don't use eval" is appropriate.  Even better is to say, "for the 
love of all that is good, textbook people, stop making newbies think 
that eval is in their toolkit, when they don't yet even know how to use 
the other tools."

> (define (confirmation target)
>   (eval '(printf "Are you sure you wish to nuke ~a?" target) namespace)
>   ...)
>
> To a purist, the above code is horrifying.

(Excepting the horrifying application domain.)  That example does show 
eval being used for no good reason.  Though usually the needless uses of 
eval are much more dangerous, and/or expensive/encumbering to maintain.

Neil V.

-- 
You received this message because you are subscribed to the Google Groups
"Racket Users" group.
To unsubscribe from this group and stop receiving emails from it, send an
email to racket-users+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

-- 
You received this message because you are subscribed to the Google Groups 
"Racket Users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to racket-users+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to